Управление без объектов в C - И почему я могу объявлять переменные в любом месте функции в C? - PullRequest
3 голосов
/ 11 мая 2011

все.На самом деле у меня есть два вопроса, несколько связанных между собой.

Вопрос № 1: Почему gcc позволяет мне объявлять переменные после операторов действия?Я думал, что стандарт C89 не позволяет этого.(Версия GCC: 4.4.3) Это даже происходит, когда я явно использую --std=c89 в строке компиляции.Я знаю, что большинство компиляторов реализуют нестандартные вещи, то есть компиляторы C, допускающие // комментарии, когда в стандарте это не указано.Я хотел бы изучить только стандарт, так что, если мне когда-либо понадобится использовать просто стандарт, я не буду цепляться за подобные вещи.

Вопрос № 2: Как сделатьВы справляетесь без объектов в C?Я программирую как хобби, и я еще не использовал язык, на котором нет Objects (он же концепции OO?) - я уже знаю немного C ++, и я хотел бы узнать, как использовать C самостоятельно.Предположительно, один из способов состоит в том, чтобы создать структуру POD и сделать функции, аналогичные StructName_constructor(), StructName_doSomething() и т. Д., И передать экземпляр структуры каждой функции - это «правильный» способ или я полностью отключен?

РЕДАКТИРОВАТЬ: Из-за небольшого замешательства, я определяю, что мой второй вопрос более четко: я не спрашиваю How do I use Objects in C? Я спрашиваю How do you manage without objects in C?, иначе как вы делаете вещи без объектов, где вы бынормально используете объекты?

Заранее большое спасибо.Я никогда не использовал язык без ООП!:)

РЕДАКТИРОВАТЬ: В соответствии с запросом, вот пример проблемы объявления переменной:

/* includes, or whatever */
int main(int argc, char *argv[]) {
    int  myInt = 5;
    printf("myInt is %d\n", myInt);
    int test = 4; /* This does not result in a compile error */
    printf("Test is %d\n", test);
    return 0;
}

Ответы [ 4 ]

3 голосов
/ 11 мая 2011
  1. c89 не позволяет этого, но c99 делает.Хотя это заняло много времени, некоторые компиляторы (включая gcc) наконец начинают реализовывать функции c99.
  2. IMO, если вы хотите использовать ООП, вам, вероятно, следует придерживаться C ++ или попробовать Objective CПопытка заново изобрести ООП, построенную поверх C снова , просто не имеет особого смысла.

Если вы все равно настаиваете на этом, да, вы можете передать указатель наструктура как имитация this - но это все еще не очень хорошая идея.

Часто имеет смысл передавать (указатели на) структуры, когда вам нужно работать с структурой данных.Однако я бы не советовал усердно работать над объединением функций в группы и заставлять их все брать указатель на структуру в качестве их первого параметра, просто потому, что так происходит в других языках для реализации вещей.

Если вам случитсяиметь ряд функций, которые работают с определенной структурой / с определенной структурой, и для них действительно имеет смысл получить указатель на эту структуру в качестве первого параметра, это замечательно - но не нужно заставлять его только потому, чтоВ C ++ все происходит именно так.

Редактировать: Что касается того, как вы обходитесь без объектов: по крайней мере, когда я пишу C, я склонен работать с отдельными персонажами чаще.Что бы это ни стоило, в C ++ я обычно получаю несколько относительно длинных строк кода;вместо этого в C я склоняюсь к множеству коротких строк.

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

Лично ябольше склоняются к использованию общего соглашения об именах в моем C-коде, поэтому (для нескольких примеров) указатели на поддеревья в двоичном дереве всегда просто называются left и right.Если я использую связанный список (редко), указатель на следующий узел всегда называется next (а если он двусвязный, другой - prev).Это очень помогает в возможности писать код, не тратя много времени на поиск определения структуры, чтобы выяснить, какое имя я использовал для чего-то это время.

1 голос
/ 11 мая 2011

Что касается ООП в C, вы смотрели некоторые темы по SO?Например, Можете ли вы написать объектно-ориентированный код на C? .

Я не могу привести пример в пример, но я думаю, что они применяют дисциплину OO-подобного в программировании ядра Linux какхорошо.

1 голос
/ 11 мая 2011

@ Вопрос № 1: я не знаю, почему нет ошибки, но вы правы, переменные должны быть объявлены в начале блока. Хорошо, что вы можете объявить блоки где угодно :). Например:

{
    int some_local_var;
}

@ Вопрос № 2: на самом деле программирование на C без наследования иногда довольно раздражает. но есть возможности в некоторой степени иметь ООП. Например, посмотрите на исходный код GTK , и вы найдете несколько примеров. Вы правы, функции, подобные тем, которые вы показали, являются общими, но конструктор обычно делится на функцию выделения и функцию инициализации. Например:

someStruct* someStruct_alloc() { return (someStruct*)malloc(sizeof(someStruct)); }
void someStruct_init(someStruct* this, int arg1, arg2) {...}

В некоторых библиотеках я даже видел какой-то полиморфизм, когда указатели на функции хранятся в структуре (которые, конечно, должны быть установлены в функции инициализации). В результате получается C ++-подобный API:

someStruct* str = someStruct_alloc();
someStruct_init(str);
str->someFunc(10, 20, 30);
0 голосов
/ 02 ноября 2014

С точки зрения изучения того, как работает C, в отличие от ОО в С ++, вам может быть проще пройти короткий курс обучения на каком-либо другом языке, который не имеет производной от ОО - скажем, Модула-2 (один измои любимые) или даже BASIC (если вы все еще можете найти реальную реализацию BASIC - в прошлый раз, когда я писал код BASIC, он был с QBASIC, поставляемым с DOS 5.0, позже скомпилированным в полном Quick BASIC).

методы, которые вы используете, чтобы добиться цели в Modula-2 или Pascal (за исключением строгой типизации, которая защищает от определенных типов ошибок, но усложняет выполнение определенных задач), в точности те, которые используются в не-OO C и работают вязык с другим синтаксисом может (возможно, IMO) упростить изучение концепций без использования ваших «программных рефлексов» и попыток выполнять операции ОО на почти знакомом языке.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...