Всем привет!
Может кто-то подсказать, как скомпилировать и прогнать Hello World ( и вообще любую Си программу) во FreeBSD? Всем спасибо!

Комментарии
09.07.2009 в 13:16

WAAAAAAAAAGH!!!!!!1111ONEONE
$ gcc helloworld.c -o helloworld
$ ./helloworld
09.07.2009 в 15:45

Распишу подробней:
Вот программа:
MAIN ()
PRINTF(“HELLO, WORLD\N”);

Вот цитата из «Язык С» Б.В. Керниган, Д.М. Ричи:

Как пропустить эту программу - зависит от используемой вами системы.
В частности, на операционной системе “UNIX” вы должны завести исходную
программу в файле, имя которого оканчивается на “.C” , например, HELLO.C
, и затем скомпилировать ее по команде
CC HELLO.C
Если вы не допустили какой-либо небрежности , такой как пропуск символа
или неправильное написание, компиляция пройдет без сообщений и будет
создан исполняемый файл с именем а.OUT . Прогон его по команде
A.OUT
приведет к выводу
HELLO, WORLD


Файл с текстом прогрммы и именем hello.c был создан в текущем каталоге.
После ввода команды CC HELLO.C система отвечает:

hello.c:2: error: syntax error before "PRINTF".

Я так понимаю, ошибка в синтаксисе?
09.07.2009 в 16:19

WAAAAAAAAAGH!!!!!!1111ONEONE
Ну логично.




видимо плохая копия учебника
09.07.2009 в 18:05

Тож же самое! Только теперь говорит уж про три ошбки (вместо двух).
Vj_o-oy, простите, вы уверены? Просто, я знаю, что это ссылка на библиотеку в VC++?
09.07.2009 в 18:19

WAAAAAAAAAGH!!!!!!1111ONEONE
_Dimitriy stdio.h - стандартный заголовочный файл, который использовался задолго до того, как VC вообще появился на свет
И да, я уверен

10.07.2009 в 13:41

Прошу прощения, я сразу не заметил, что это форма, в которую всталвлен код (я увидел только заголовок).
Да, я открыл файл hello.c в vi, ввёл туда весь выше приведенный код, сохранил. Далее, ввожу:
$ gcc hellо.c -o hello
Отвечает:
/var/tmp//ccfPW2FK.o: In function 'main':
/var/tmp//ccfPW2FK.o(.text+0x19): undefined reference to 'PRINTF'
10.07.2009 в 16:51

WAAAAAAAAAGH!!!!!!1111ONEONE
Си - регистрозависимый язык. Я не знаю почему в примере printf набрано капсом, в моем коде оно записано в нижнем регистре.
10.07.2009 в 23:13

Благодарю! Всё получилось!
А, можно узнать подробности о введенных командах? Ведь, они не совпадают с теми, что в книге!?
11.07.2009 в 01:00

WAAAAAAAAAGH!!!!!!1111ONEONE
_Dimitriy может лучше в аське? ;)
11.07.2009 в 18:23

IDDQD - Команда молодости нашей, команда, без которой мне не жить.
_Dimitriy может лучше в аське? ;)
Тут разумней хороший букварь предложить. :)
11.07.2009 в 18:41

WAAAAAAAAAGH!!!!!!1111ONEONE
Flex Ferrum кстати да
_Dimitriy тут много умного: opennet.ru
12.07.2009 в 00:43

Информация обычно не запоминается, пока она не является ответом на вопрос.
12.07.2009 в 00:52

IDDQD - Команда молодости нашей, команда, без которой мне не жить.
Информация обычно не запоминается, пока она не является ответом на вопрос.
Попробуй прочитать здесь:
Первая программа

Тут, правда, в варианте для C++, но суть (в основном) та же.
13.07.2009 в 22:20

Всем привет!
Flex Ferrum, прочитал, спасибо, пазнавательно! Какой бы ты следущий порекомндовал шаг?
Vj_o-oy, а можешь подсказать какую-нибудь асю для FreeBSD?
14.07.2009 в 21:47

IDDQD - Команда молодости нашей, команда, без которой мне не жить.
Flex Ferrum, прочитал, спасибо, пазнавательно!
Спасибо. :)
Какой бы ты следущий порекомндовал шаг?
Все зависит от того, куда ты хочешь придти. ;)
14.07.2009 в 23:48

WAAAAAAAAAGH!!!!!!1111ONEONE
_Dimitriy centerICQ, если консоль. Если графика, то смотря какая оболочка
16.07.2009 в 17:59

Не работает во FreeBSD следущая программма, взатая и того же Кернигана и Ричи. Програма пересчёта температур из Фаренгейта в Цельсий.
Вот такие система выдаёт сообщения:
# cc 123.c (это имя файла)
123.c: In functin 'main':
123.c:5: error: syntax error before "lower"
Вот сама программа:
# include
int main (void)
/Дальше копирую из книги капсом/
INT LOWER, UPPER, STEP;
FLOAT FAHR, CELSIUS;
LOWER = 0; /* LOWER LIMIT OF TEMPERATURE
TABLE */
UPPER =300; /* UPPER LIMIT */
STEP= 20; /* STEP SIZE */
FAHR = LOWER;
WHILE (FAHR <= UPPER)
{
CELSIUS = (5.0/9.0) * (FAHR -32.0);
PRINTF(“%4.0F %6.1F\N”, FAHR, CELSIUS);
FAHR = FAHR + STEP;
}
16.07.2009 в 21:55

IDDQD - Команда молодости нашей, команда, без которой мне не жить.
_Dimitriy, а можешь дать ссылочку на книгу, откуда ты это скопировал?
И это, скопируй сюда исходник, который ты отправляешь на компиляцию. Символ в символ.
16.07.2009 в 22:51

Книга есть вот lib.ru/CTOTOR/kernigan.txt
Исходник сюда скопировать не могу (пока не могу). Он у меня в другой ОС, а она на другом винте.
По ходу, пару вопросов:
1. Во FreeBSD я захожу в сеть по команде links "адрес". Почему то все тексты там транслитом!?
2. Каким-то чудом скачал Оперу. Она у меня лежит там в текущем каталоге. Как её распаковать (установить)?
3. Текст исходника у меня там в vi. Как я могу его скопировать сюда?
16.07.2009 в 23:36

WAAAAAAAAAGH!!!!!!1111ONEONE
_Dimitriy во-первых: листинги, набранные капсом, не будут сейчас уже нигде правильно компилироваться/транслироваться. Большая часть стандартных функций имеет названия в нижнем реистре.
Если опера в формате .tar.bz2 или tar.gz, то распаковать это дело через tar
$ xvf название_архива
но, что дальше, я уже не помню. Вообще рекомендую почитать чего-нибудь про bash, это может очень помочь. bash - одна из основных командных оболочек в *nix. Либо уже стучаться мне в аську
16.07.2009 в 23:52

во-первых: листинги, набранные капсом, не будут сейчас уже нигде правильно компилироваться/транслироваться. Большая часть стандартных функций имеет названия в нижнем реистре.
Я уже это понял. В vi у меня всё набрано в нижнем регистре.
Вообще рекомендую почитать чего-нибудь про bash, это может очень помочь. bash - одна из основных командных оболочек в *nix.
Вообще-то, я читаю сейчас одну большую толстую книгу по UNIX, и читаю проект документаци по FreeBSD freebsd.org.ua
Просто инфы настолько много, и она настолько разобщена, что я пока что, могу только погружаться в среду, очень медленно.

Либо уже стучаться мне в аську
centerICQ, если консоль. Если графика, то смотря какая оболочка
А, как узнать свою оболочку? # - это приглашение моей командной строки.
17.07.2009 в 00:11

WAAAAAAAAAGH!!!!!!1111ONEONE
_Dimitriy основные оболочки: KDE, GNOME. Везде есть какая-нибудь ботва в духе "About". Если нету, то ставь centerICQ. На первое время хватит. Вообще лезть во фряху без подготовки не рекомендуется. Это не какая-нибудь сиране Ubuntu, где интерфейс проще маздая.
# - приглашение командной строки для суперпользователя (root)
$ - приглашение командной строки для простого смертного (не root)

У меня букварь по никсам лежит за авторством некоего Армстронга "секреты UNIX". Довольно толковый и очень толстый (~1000 страниц) букварь, но лучше, если есть представление о теме разговора.

Вообще, прежде, чем заниматься разработкой, есть смысл освоить ОС как пользователь. Либо пересесть на другие никсы (ту же сиране Ubuntu), как более юзер-френдли вариант, а потом уже углубляться во всякие фряхи и куэныгзы.

Какова цель изучения?
17.07.2009 в 00:52

Don't stop the music.
_Dimitriy
Компилятор языка си чувствителен к регистру букв. Это значит, что если вы напишете например:
pRinTF(""); или PRINTF(""); то программа не скомпилируется. А если printf(""); то скомпилируется. Учебник Кернигана и Ричи (первое издание) был написан в 1978 году, когда этой особенности языка си не было.

Чтобы вы сразу так сказать "вошли в струю". Вот:
В языке си приняты следующие т.н. соглашения о написании кода:

Заглавными буквами обозначаются строковые константы (что это такое вы прочитаете в учебнике), например:
#define HOLMES_HOME_ADDRESS "Baker street 221" //Это строковая константа которая равна строке "Baker street 221"

В именах переменных, функций, типов и т.д. могут строчные буквы например max(int n, int m) //Это функция. int node //Это переменная. или если название функции или переменной состоит из нескольких слов то первое слово пишется строчными, и каждое из остальных слов пишется строчными за исключением его первой буквы. Пример: getDefaultPosition(Point p); //Это функция. char currentLetter; //Это переменная.

Об остальных свойствах кодовых соглашений (code conventions) вы можете прочитать в интернете.

Теперь об остальных особенностях вашего кода и почему "ругается" компилятор:

Рассмотрим строку: int main (void). В теле функции main() после всех инструкций должна стоять команда return 0; У вас её нет. Поставьте её и ни в коем случае не принимайте на веру "потому что так надо" а обязательно уясните почему этот return 0; там должен быть. Об этом написано далее в учебнике.

Рассмотрим две строки:
#include

и

printf(“%4.0f %6.1f\n”, fahr, celsius);

У вас вызывается функция printf() которая лежит в библиотеке (наборе функций) доступ к которой осуществляется через файл stdio.h. Это очень грубое но думаю, что понятное объяснение. Команда #include которая у вас пустая ответственна именно за то чтобы включить файл stdio.h в ваш файл. В вашем же коде нет вызова stdio.h. И поэтому компилятор не "знает", что printf() это не бессмысленный набор букв, а вызов функции. Поэтому "ругается".

Далее. Общий вид функции main такой:
int main()
{
//Какой-нибудь код.
return 0;
}

Т.е. тело функции всегда начинается и заканчивается фигурными скобками. То что в теле - пишется с отступом. Так легче читать и воспринимать код. В вашем коде тело функции не обрамлено фигурными скобками.

В остальном код верен.

Общие слова:
Вы совершаете типичные ошибки новичков, и это нормально :). Если вы решили стать программистом, то ничего не воспринимайте как догму. Крутите вертите то что вы прочитали, экспериментируйте с этим, совершайте ошибки. И тогда придёт понимание и умение.
17.07.2009 в 01:14

IDDQD - Команда молодости нашей, команда, без которой мне не жить.
Учебник Кернигана и Ричи (первое издание) был написан в 1978 году, когда этой особенности языка си не было.
А пруфлинк можно? :shuffle: Сдается мне, что C регистрозависим от рождения, а примеры в капсе (в приведенном учебнике) - это "тонкости перевода", за которые надо бы руки оторвать... Я С изучал как раз по первому (еще советскому) переводу этой книги, и там с регистром все было впорядке. ;)

Если не удасться найти более современного учебника, можно (на крайняк) воспользоваться этим:
Язык программирования С++. Второе издание
Актуальность его оставляет желать много лучшего, но, по крайней мере, с регистром все в порядке.
17.07.2009 в 01:37

Don't stop the music.
Flex Ferrum

Верно, он с самого начала регистрозависим. Руки оторвать переводчикам.

У меня K&R нормальный ).
17.07.2009 в 01:41

IDDQD - Команда молодости нашей, команда, без которой мне не жить.
Руки оторвать переводчикам.
Не переводчикам, а тому, кто сканировал. Перевод на русский - в абсолютной норме! В бумажном варианте.
17.07.2009 в 16:17

Какова цель изучения?
Необходимо научиться писать программы на си.
Рассмотрим строку: int main (void). В теле функции main() после всех инструкций должна стоять команда return 0;
Прошу прощения, там, в исходнике, она есть, здесь я забыл её вписать. Как я уже писал, я не знаю, как скопировать текст исходника, то бишь, я ещё не научился заходить в сеть из FreeBSD.
В вашем коде тело функции не обрамлено фигурными скобками.
Где должна стоять первая фигурная скобка? Я варьировал в исходнике, строчкой выше, строчкой ниже, система ругалась длинным перечнем ошибок, тольков этом месте выдаёт всего одну ошибку:

# cc 123.c (это имя файла)
123.c: In functin 'main':
123.c:5: error: syntax error before "lower"


Где должны объявляться переменные? В теле функции? До? А где начинается функция?
17.07.2009 в 17:46

Don't stop the music.
_Dimitriy
Где должна стоять первая фигурная скобка?

Посмотрите ещё раз на общее строение функции:

int main()
{
//Какой-нибудь код.
return 0;
}

int main() - это заголовок функции.
Тело функции находится внутри фигурных скобок.

Где должны объявляться переменные? В теле функции?
Да, за очень редким исключением.

А где начинается функция?
Допустим есть код:
#include <stdio.h>

void f1()
{
//Helping function number 1.
}

int f2()
{
//Helping function number 2.
return 1;
}

int f3()
{
//Helping function number 3.
return 2;
}

Здесь я реализовал три вспомогательные функции f1, f2, f3. Как видите они начались сразу после команды #include <stdio.h>. Это обычный но не общий случай. О других случаях вы узнаете дальше.

Теперь я напишу главную (main) функцию которая будет их вызывать:

int main()
{
f1();
printf("Printing number %d\n", f2());
printf("Printing number %d\n", f3());
return 0;
}

Обратите внимание, что значение возвращаемое функцями f2(), f3() может быть аргументом для другой функции (например printf()) и что функция f1() возвращает значение пустого типа (void) т.е. её цель - выполнить определённые действия внутри её тела и только.
17.07.2009 в 19:34

Ок, где же ошибка?
Копирую ещё раз программу с переставленой круглой скобкой:

# include
int main (void)
{
INT LOWER, UPPER, STEP;
FLOAT FAHR, CELSIUS;
LOWER = 0; /* LOWER LIMIT OF TEMPERATURE
TABLE */
UPPER =300; /* UPPER LIMIT */
STEP= 20; /* STEP SIZE */
FAHR = LOWER;
WHILE (FAHR <= UPPER)
CELSIUS = (5.0/9.0) * (FAHR -32.0);
PRINTF(“%4.0F %6.1F\N”, FAHR, CELSIUS);
FAHR = FAHR + STEP;
return 0;
}
17.07.2009 в 21:31

Don't stop the music.
_Dimitriy

Здесь две ошибки.

Первая: нет вызова библиотеки stdio.h
Вторая: В цикле выполняется только одна инструкция: celsius = (5.0 / 9.0) * (fahr - 32.0). То есть до тех пор пока fahr <= lower - значение справа заходит в переменную celsius.

Общий вид цикла while:

while(//здесь выражение которое проверяется на истинность)
{
//Какой-то код.
}

Если скобок после while нет - то по умолчанию выполняется только одна инструкция на следюущей строке.