Модераторы: bsa

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Связывание нескольких .cpp компилятором, Хранение функций во внешнем файле 
V
    Опции темы
yorm
Дата 20.1.2008, 11:25 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 15
Регистрация: 1.10.2006

Репутация: нет
Всего: нет



Здравствуйте

Начал изучение c++, поэтому в специфичной терминологии еще плаваю. Помогите, пожалуйста, разобраться:

Хотелось функции хранить в отдельном файле и в основной подгружать только необходимые. Решил следующим образом

main.cpp - основной файл
Код

#include <iostream.h>

extern int test1();

extern char test4[];
extern int test5;

int main() {
    cout << "int test1(): " << test1() << endl;
    cout << "char test4[]: " << test4 << endl;
    cout << "int test5: " << test5 << endl;
    return 0;
}


func.cpp - здесь хранятся вызываемые функции
Код

int test1() {
    return 111;
}

int test2() {
    return 112;
}

char test3() {
    return 's';
}


vars.cpp - здесь хранятся переменные
Код

char test4[] = "test1";
int test5 = 11;


для компиляции использовал Borland C++ 5.6 for Win32 компилятор (из дистрибутива Borland C++ Builder)
bcc32 main.cpp func.cpp vars.cpp

А теперь, собственно, вопрос:
1. Действительно ли при компиляции в результирующий main.exe добавились только extern int test1(); extern char test4[]; extern int test5; или остальные функции и переменные из внешних файлов тоже там присутствуют?
2. При компиляции корневым (начальным) указывается первый .cpp в строке или порядок не важен?
3. Правильный ли способ я использую или можно каким-то другим образом хранить функции в отдельном файле и включать только необходимые? (#include, насколько я понял, включает файл целиком?)


PM MAIL   Вверх
MAKCim
Дата 20.1.2008, 11:41 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 2
Всего: 207



Цитата(yorm @  20.1.2008,  11:25 Найти цитируемый пост)
Действительно ли при компиляции в результирующий main.exe добавились только extern int test1(); extern char test4[]; extern int test5; или остальные функции и переменные из внешних файлов тоже там присутствуют?

не определено однозначно
хотя конкретно для BC можно узнать наверняка
Цитата(yorm @  20.1.2008,  11:25 Найти цитируемый пост)
При компиляции корневым (начальным) указывается первый .cpp в строке или порядок не важен?

не важен
Цитата(yorm @  20.1.2008,  11:25 Найти цитируемый пост)
Правильный ли способ я использую или можно каким-то другим образом хранить функции в отдельном файле и включать только необходимые? (#include, насколько я понял, включает файл целиком?)

extern-ы принято помещать в .h файл


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
archimed7592
Дата 20.1.2008, 11:44 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 6
Всего: 93



Статические переменные с внешним связыванием(т.е. как у тебя) будут включены обязательно. По крайней мере, по Стандарту.


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
yorm
Дата 20.1.2008, 13:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 15
Регистрация: 1.10.2006

Репутация: нет
Всего: нет



Цитата(archimed7592 @  20.1.2008,  11:44 Найти цитируемый пост)
Статические переменные с внешним связыванием(т.е. как у тебя) будут включены обязательно. По крайней мере, по Стандарту.

Это понятно. Интересовало - будут ли включены функции test2() и test3 из func.cpp. Сейчас посмотрел exe-шник, вроде нигде не присутствуют

Цитата(MAKCim @  20.1.2008,  11:41 Найти цитируемый пост)
extern-ы принято помещать в .h файл 

Понял. Т.е.
func.h
Код

extern char test4[];
extern int test5;

main.h
Код

#include <iostream.h>
#include "func.h"
extern int test1();

int main() {
    cout << "int test1(): " << test1() << endl;
    cout << "char test1[]: " << test4 << endl;
    cout << "int test5[]: " << test5 << endl;
    return 0;
}

*.h - это интерфейс, который должен быть реализован в одном из скомпилированных файлов, к которому он подключен?

PM MAIL   Вверх
MAKCim
Дата 20.1.2008, 13:38 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 2
Всего: 207



yorm, 
в .h файле не должно быть (кроме случаев, когда ты знаешь, что делаешь) определений, только объявления
в твоем случае надо делать так
Код

// def.h

extern char test4[];
extern int test5;
extern int test1();

Код

// main.cpp

#include <iostream.h>
#include "def.h"

int main() {
    cout << "int test1(): " << test1() << endl;
    cout << "char test1[]: " << test4 << endl;
    cout << "int test5[]: " << test5 << endl;
    return 0;
}



--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
yorm
Дата 20.1.2008, 14:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 15
Регистрация: 1.10.2006

Репутация: нет
Всего: нет



Спасибо за консультацию!
PM MAIL   Вверх
archimed7592
Дата 20.1.2008, 15:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 6
Всего: 93



Цитата(yorm @  20.1.2008,  13:27 Найти цитируемый пост)
Интересовало - будут ли включены функции test2() и test3 из func.cpp.

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


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
MAKCim
Дата 20.1.2008, 18:06 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 2
Всего: 207



Цитата(archimed7592 @  20.1.2008,  15:50 Найти цитируемый пост)
хотя, не исключено, что линкер настолько туп, что умеет выбрасывать из итогового файла только модули целиком

выходит, что LD туп  smile 
не, на самом деле это довольно нетривиальная задача


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
archimed7592
Дата 20.1.2008, 18:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 6
Всего: 93



А в чём нетривиальность заключается? 0_о 


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
MAKCim
Дата 20.1.2008, 19:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 2
Всего: 207



archimed7592, 
скажем так, не нетривиальная, а доволно сложная  smile 
представь себе набор объектных файлов, которые поступают на вход компоновщику
каков алгоритм его работы?
в случае LD в качестве алгоритма выступает скрипт, который ставит в соответствие секциям входных объектных файлов секциии выходного
если не смотреть на то, что на самом деле используется, а что нет, то все крайне просто: берется секция входного объектного файла и помещается по определенному смещению в выходной
если смотреть на факт использования, то для каждой секции входного объектного файла нужно найти символы, которые определены в ней
для каждого такого символа нужно находить все релокации в других объектных файлах, которые ссылаются на этот символ
если эти другие объектные файлы не являются контейнером для main(), то необходимо определить контекст релокации, т. е в контексте определения какого символа находится релокация и, определив, продолжить процесс рекурсивно
причем есть вероятность того, что этот процесс породит бесконечную рекурсию
кроме того, не факт, что символ, на который есть релокация в другом символе, определенном в модуле с символом main, действительно не используется


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
archimed7592
Дата 20.1.2008, 19:31 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 6
Всего: 93



Цитата(MAKCim @  20.1.2008,  19:11 Найти цитируемый пост)
причем есть вероятность того, что этот процесс породит бесконечную рекурсию

Цикличность графа отслеживать не судьба? smile

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


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
MAKCim
Дата 20.1.2008, 22:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 2
Всего: 207



Цитата(archimed7592 @  20.1.2008,  19:31 Найти цитируемый пост)
и вкладывать эту информацию в объектник

не забываем, что форматы файлов специфицированы и просто так добавить какую-то информацию туда нельзя  smile
кроме того, вот пример ситуации, при которой компоновщик обламывается
Код

/* main.c */
extern int foo();

int main() {
    return foo();
}
 
Код

/* functions.S */

.text
some:
    nop
    nop
    ret
.globl some
1:
    call    routine
    ret
foo:
    jmp   1b
.globl foo

Код

/* routine.S */

.text
routine:
    xorl    %eax, %eax
    ret
.globl routine

вообщем, есть три файла: main.c, functions.S, routine.S
при компиляции получаем 3 объектных файла: main.o, functions.o, routine.o
подаем их на вход компоновщику и...
попробуй догадаться, почему конечная программа не будет работать, если компоновщик будет отслеживать зависимости по приведенному выше алгоритму  smile

Добавлено через 2 минуты и 47 секунд
Цитата(archimed7592 @  20.1.2008,  19:31 Найти цитируемый пост)
На самом деле, если, в придачу, компилятор будет отслеживать зависимости(те что он может отследить - т.е. в пределах объектника)

как быть с callback-функциями?
не все так просто


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
warmonger_
Дата 20.1.2008, 23:13 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 155
Регистрация: 7.7.2007
Где: г. Киев

Репутация: 1
Всего: 3



Цитата(yorm @  20.1.2008,  13:27 Найти цитируемый пост)
будут ли включены функции test2() и test3 из func.cpp

что бы этого точно не было, нужно пользоваться пространством имен

Это сообщение отредактировал(а) warmonger_ - 20.1.2008, 23:14
--------------------
Make everything as simple as possible, but not simpler.Albert Einstein
PM MAIL   Вверх
JackYF
Дата 20.1.2008, 23:15 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


полуавантюрист
****


Профиль
Группа: Участник
Сообщений: 5814
Регистрация: 28.8.2004
Где: страна тысячи озё р

Репутация: 6
Всего: 162



Цитата(warmonger_ @  20.1.2008,  22:13 Найти цитируемый пост)
нужно пользоваться пространством имен

А, по-моему, это чисто логическое отделение функций/классов, и линковищку на пространства имён с глубокой высокой башни.
Поправьте меня, если я не прав.



--------------------
Пожаловаться на меня как модератора можно здесь.
PM MAIL Jabber   Вверх
MAKCim
Дата 20.1.2008, 23:16 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 2
Всего: 207



Цитата(warmonger_ @  20.1.2008,  23:13 Найти цитируемый пост)
что бы этого точно небыло, нужно пользоваться пространством имен

пространства имен здесь не причем

Добавлено через 2 минуты и 53 секунды
Цитата(JackYF @  20.1.2008,  23:15 Найти цитируемый пост)
А, по-моему, это чисто логическое отделение функций/классов, и линковищку на пространства имён с глубокой высокой башни.
Поправьте меня, если я не прав.

 smile 
прав



--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
Страницы: (3) Все [1] 2 3 
Ответ в темуСоздание новой темы Создание опроса
Правила форума "C/C++: Для новичков"
JackYF
bsa

Запрещается!

1. Публиковать ссылки на вскрытые компоненты

2. Обсуждать взлом компонентов и делиться вскрытыми компонентами

  • Действия модераторов можно обсудить здесь
  • С просьбами о написании курсовой, реферата и т.п. обращаться сюда
  • Вопросы по реализации алгоритмов рассматриваются здесь


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, JackYF, bsa.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Для новичков | Следующая тема »


 




[ Время генерации скрипта: 0.0587 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.