Я работаю над небольшим приложением, написанным на C ++, и хочу использовать его на своей платформе. К сожалению, только в нашей кросс-компиляции инструментарий (надежно) предоставляет компилятор Си. Я посмотрел на приложение, и оно довольно простое и использует только идиомы, специфичные для C ++, в нескольких местах, поэтому я решил просто преобразовать его в C-код вручную.
Я наткнулся на одну строку, что я не уверен, как справиться. Код использует Termios, чтобы открыть новый порт для связи с потоком TTY, и инициализирует структуру Termios, используя new
ключевое слово.
termios *settings = new termios();
Насколько я понимаю, new
Ключевое слово, помимо выделения соответствующей памяти, вызывает инициализатор объекта. В С после того, как я выделю память malloc
можно вручную вызвать инициализатор? Нужно ли мне?
У меня такое ощущение, что я неправильно понимаю что-то очевидное / фундаментальное или что я смотрю на все это неправильно. Я не очень привык к C ++ коду.
редактировать: я, кажется, вызвал некоторую путаницу. Строка кода выше создает новую структуру termios, как определено в termios.h
часть стандартных библиотек в большинстве реализаций C.
Линия
termios *settings = new termios();
выделяет память для termios
объект и значение инициализирует Это. поскольку termios
является POD, эквивалентный C будет
struct termios* settings = calloc(1, sizeof(*settings));
или же
struct termios* settings = malloc(sizeof(*settings));
memset(settings, 0, sizeof(*settings));
и, конечно, эквивалент delete settings
было бы free(settings)
,
Я бы предложил создать функцию
termios *new_termios()
это объединит malloc с кодом конструктора. После этого не используйте malloc для выделения termios
,
«В C, после того как я выделил память с помощью malloc, могу ли я вручную вызвать инициализатор?
К сожалению, вы не можете.
Нужно ли мне?»
Это действительно зависит от определения termios
объекты. В основном, что malloc
делает это просто выделить кусок памяти. То есть он не выполняет инициализацию и распределение внутренней памяти, как конструктор.
Что я делаю в этих ситуациях:
Я создаю функции-оболочки C для своих объектов C ++ с помощью непрозрачных указателей. Например, чтобы вызвать конструктор объекта C ++, я бы создал оболочку C ++ для C в .cpp
файл:
void* create_termios() { return new termios(); }
void destroy_termios(void *obj) { delete obj; }
// other wrapper functions for termios
И тогда я бы сопряг эти функции в C с .h
файл:
extern "C" {
void* create_termios();
void destroy_termios(void *obj);
// declare any other necessary wrappers
}
Заметить, что termios
это имя struct
относится к termios (3) функция, так что лучше не использовать это termios
имя в программе Linux или POSIX на C (т.е. не называйте ваши типы обычными типами, предоставляемыми системными библиотеками).
Кстати, вы должны рассмотреть возможность использования некоторых существующий Терминал IO библиотека, как Ncurses или же Readline
Наконец, если вы настаиваете на том, чтобы иметь свой собственный termios
структура или класс (что на самом деле очень плохая идея, выберите другое имя), управляемый вашей библиотекой C ++ для вызова из C, вы должны обернуть его в allocator + constructor & деструктор + деаллокатор, как это.
extern "C" struct termios* make_my_termios () {
struct termios* ts = new termios;
return ts;
}
extern "C" void destroy_my_termios(struct termios* ts) {
delete ts;
}
И если вы просто используете подлинный struct termios*
(от termios (3)) в вашей библиотеке C ++, просто оставьте все как есть …