GCC - The Complete Reference (537669), страница 45
Текст из файла (страница 45)
При использовании команды д++ по умолчанию применяется стандартная библиотека С++. Распространенным способом является размещение объявлений функций в заголовочном файле ()зеадег 6)е) и применение объявления ехеегп "с" ко всему содержимому этого файла. При этом применяется стандартный для языка С++ синтаксис, как показано в следующем примере: ехсегп "с" ( 1пс в11вьсау(апе 1снепй, 1пс ЬвдЬепй)г уо1й ирйасайЕВС(СЬаГ вПЕнйЕВС)Г йоиЬ1Е дверее(СЬаГ влаВЕ)( Вызовы функций С++ из кода на языке С Чтобы программа на языке Смогла вызывать функцию из программы на С++ несбходимо, чтобы вызываемая функция С++ поддерживала последовательность вызова, сооответствующую языку С.
Следующий пример демонстрирует синтаксис создания вызываемой из программы на языке С функции программы на С++: /* сррвауЬе11о.срр */ алпс1ийе <1овегеав> ехеегп "С" уо1й сррвауЬе11о(сЬаг *все]г тсьй сррвауЬе11с(сЬаг 'вег) ( вей:георг « всг « «хп"; ) Несмотря на то, что функция сррвауЬе11о() объявлена как ехеегп "с", она является частью программы на языке С++. Это означает, что код самой функции в действительности является кодом на языке С++.
Вы вполне можете создавать и ослсбсждать объекты внутри этой функции. Кроме того, при необходимости обратного вызова из функции сррвауЬе11о ( ) функции из программы на С вам придется объявить вызываемую функцию как ехсегп "Сгч Иначе компилятор воспримет вызываемую функцию как функцию С++ и соответственно преобразует ее имя. Далее — программа на языке С, вызывающая рассмотренную выше функцию С++: /* с2срр.с */ ьпс ваап(1пс агдс,сЬаг *агд г()) ( сррвауЬе11о("Ие11о Йгов С Ео С++") гееигп(с)г ) 200 Часть Н. Использование Сборного Компилятора Следующая последовательность команд выполнит компиляцию и компоновку програл]мы с2срр: 3 д++ -с сррвауЬе11о.срр -о сррвауЬе11о.о а дсс -с с2срр.с -о с2срр.о 3 дсс сррвауЬе11о.о с2срр.о -1вег)с++ -о с2срр Совмещение языков ОЦесбче-С и С Благодаря тому что язык ОЬ/ес//те-С представляет собой не что иное, как расширениее языка С добавлением поддержки классов, довольно просто комбинировать исходные модули, написанные на этих языках.
Последовательности вызова в этих языках совпадают, поэтому остается только просто вызвать функцию. Вызов С-функции из программы на языке ОЬ)есбче-С Следующая программа ОЬ)ес(!те-С передает адрес перел]енной строкового типа в функцию на языке СсвауЬе11о(); /* оЬЗс2с.в </ дгврогс <вс<)го.Ь> хпс вахп(апс агдс,сЬаг *агдт()) ( свауЬе11о("Не11о хгов ОЬзесх1уе-С Ео С")г хееигп(0)] ) Функция с вауЬе11о () передает эту строку на стандартное устройство вывода: /* свауЬе11о.с */ $1пстиг)е <всг)хо.Ь> тоЫ свауЬе11о(сЬаг ьвхг] ( рг1пех("ЪвХп",вег)г ) Следующая последовательность из трех команд компилирует программу оЬз с2с и компонует полученный объектный код в готовый к запуску файл.
При компоновке следует указывать опцию -1оЬз с для подключения стандартной разделяемой библиотеки языка ОЬ/ес//те-С. а дсс -ипо-1вроге -с оьзс2с.в -о оь302с.о 3 дсс -с свауЬе11о.с -о свауЬе11о.о 3 дсс оЬ5сас.о свауЬе11о.о -1оЬЗс -о оЬ3сзс Вызов функции ОЬ1есбче-С из программы на языке С Программа в следующем примере вызывает написанную в синтаксисе ОЬ/есг/теС функцию оЪзсвауЬе11о(): Главе 10. Совмещение языков 20 1( /* сзоЬзс.с "/ 1пс паап(апт агдс, сЬаг >агдсу() ) ( оьзсвауье11о("ие11о гтса с го ОЬзесеаие-с")у гетигп(0)у ) Далее следует код вызываемой функции на языке ОЬ/ес/уие-С: /* овзсвауве11о.ю "/ Мюротг <оЬ5с/ОЬ~есЕ.Ь> Мьаротг "Яреаиъапе.Ь" ис1ут оЬЗсвауЬе11с(сЬаг *вгт) ( 1<1 вреа1су вреаи = 1яреаиъапе пеа)у (вреаи вегясгапду вгт)у (вреа)с вау)у (вреа)с гтее)у ) Как видите, функция ОЬз с вауЬе11о ( ) создает экземпляр объекта Яре а)сыпи, записывает в него символьную строку и затем использует метод яау этого обьекта для вывода строки.
Далее вам предлагаются листинги заголовочного файла ()уеа()ег 61е) объекта яреа)сьхпе и файла с кодом его реализации (ппр!епуеп(а()оп й!е): /* Яреа1сьапе.Ь */ $(арогт <оЬЗс/ОЬЗесЕ.Ь> В1птегЕасе Яреакъ1ПЕ у ОЬзесг ( сваг *вет1пду - весястапду (сЬаг *) всгу - вауу - Егееу Вепуз /* Яреа)съгпе.ю */ (((арсгт "Яреаиъапе.Ь" В1юр1еюепгатаоп яреаКЫпе + пеа ( ве1Е = (вирет пеа1 у тегитп ве1ту - весятг1пду (сЬаг *)вгг вгг1пд = вегу гесигп ве1ту ) - вау ( ртапег("усе~и",вегапд)у 202 Часть И. Использование Сборного Компилятора гесигп ве1гг ) — ггее ( гееигп (вирег ггее] ) Следующая последовательность из четырех команд компилирует весь набор исходных файлов в объектный код и затем компонует два полученных объектных файла в готовую программу: Я дсс -Ипо-ашрогс -с оЬЗсвауие11о.ш -о оЬЗсвеуие11о.о Я дсс -Ипо-?шрогс -с Ярееиь?пе.ш -о ЯревКИпе.о Ф дсс -с с2оЬЗс.с -о с2оЬЗс.о Я дсс с2оЬЗс.о оЬзсвеуие11о.о Ярееиьапе.о -1оЬЗс -о с2оЬзс Сочетание языков Зача и С++ существует возможность использования интерфейса сн1 (сокращение от "суяппз Майке ]п(ег(асе") для доступа к классам /ага из программ на языке С++.
Два этих языка довольно сильно различаются между собой, но все же они имеют определенные фундаментальные сходе~на: ° Классы объявляются по имени и наследуют свойства других классов. ° Классы содержат функции, они могут замешаться (перегружаться) по соответствию параметров. ° Применяемые типы данных имеют прямые соответствия между языками.
° Правила построения выражений в языке Уага наследуют синтаксис выражений языка С. бСС компилирует классы и языка С++ и языка Уага сходным образом. Благодаря атому необходимо только избегать ситуаций, которые могут возникать по причине наиболее принципиальных различий этих языков. Иногда требуется специально вносить в код поправки, делающие возможным использование классов, написанных на языке /ага.
Создание Зача-объектов и вызов статических методов Следующий пример программы создает объект Уага-класса 2аиа. 1апд. Ясгдпд и передает его методу дауа.?апд. Яувееш.оие () для вывода: /* сп1вегоие.ори */ «(пс1иае <дсЗ/сп?.Ь> $1пс1иае <Зава/1впд/Яувсеш.Ь> $?пс1иде <Зета/ао/Ргапсасгеаш.и> апс шеап(1пе егдс, сиег <егду) ( авив:г1впд::Ясг1пд *всг? Глава 1О. Совмещение языков 203 дчсгеасетачачм[ипьь)~ Очдссас)гоиггепстдгеад(пцЬЬ,ИОЬЬ) вег = дчиеияегьпдьае1п1("ие11о ггое с++ ео дача" ); зачв::1апд::вчвееею:оие->ргьпетп(вег); дчпееасисиггепетьгевв()г ) Эта программа может быть скомпилироваиа и скомпонована следующей командой: > д++ спьвегоие.срр -1дсз -о опьехсереьоп Заголовочный файл сп1.)з содержит прототипы функций, необходимые для задействования интерфейса С)>) !. Также в программе имеются директивы ййпс1ибе, которые подключают классы зача.1апд.вувееш и зача.1о.рг1пеЯегеат.
Несложио было бы также подключить и «ача.1апд. Яег1пд, ио это уже было бы излишним, поскольку этот класс вместе с некоторыми другими заголовочными файлами (Ьеас)ег 61ез) системного уровня всегда подключается в опь.)ь В языке авиа для обработки классов используются ссылки на иих (геуегепсез), поэтому для хранения адреса объекта з ача. 1апд Явгйпд объявляется собственный указатель. Полное имя, применяемое для описания дауа-класса в синтаксисе языка С++, включает в себя пару двоеточий (":: ").
Следует соблюдать это соглашение об именах при каждом обращении к авиа-классу по имени, если для него не определеяо именное пространство. Например, классы яегйпд и яувееш могут быть объявлеиы и использованы следующим образом: иввпд паееврасе дача::1апдг вег1пд *лег> Вувсеп.оис->ргвпс1п(вкг) Вызов функции дчсгеаеедачачм() инициализирует среду выполнения Уаюпрограмм. Это включает в себя установку Уага-иитерфейса управления потоками, организацию динамического распределения памяти ("яагЬаяе со!1есйоп" — буквально "сборка мусора") и обработки исключений.
Эта функция должна быть вызвана в программе один раз до создания классов /ага и использования их методов. Вызов функции ючде еао)зсиггепет)тгеаг1 тачачм ( ) регистрирует процесс, порождаемый вызывающей программой, в предварительно инициализированной среде виртуальной машины Зауа. ("Зача Ч(ппа( Мазй|пе" или Л'М вЂ” интерпретатор, вылалияющий код программ иа языке /ага.) Эта функция также должна быть вызвана в программе один раз до создания зауа-классов и использования методов /ага, но только после вызова гчсгеаеедачачм(). В коице программы вызов функции юч))есас)гсиггепЕТ)згеай() снимает процесс, ранее зарегистрированный вызовом функций дчсгеаеедачарм() и ачвееас)тсиггепет)тгеабдачачм() . При завершении это гарантирует "чистый выход" — полное освобождение ресурсов, занимаемых приложением.