- 01
- 02
- 03
- 04
- 05
- 06
- 07
- 08
- 09
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
#include <iostream>
#include <functional>
using namespace std;
struct T
{
int a;
T(const T&):a(1){cout<<"copy_construct T"<<endl;}
T():a(1){cout<<"construct T"<<endl;}
~T(){a=0;cout<<"destruct T"<<endl;}
const T& operator=(const T&){cout<<"copy_ass T"<<endl;return *this;}
};
struct M: public T{};
void f(const T& fa)
{
cout<<"fa.a= "<<fa.a<<endl;
}
int main() {
f(std::cref(T()));
cout<<endl;
const T& b = T();
cout<<"b.a= "<<b.a<<endl;
cout<<endl;
const T& a = std::cref(T());
cout<<"a.a= "<<a.a<<endl;
return 0;
}
LispGovno 03.12.2012 18:25 # 0
defecate-plusplus 03.12.2012 18:40 # +4
reference_wrapper нельзя использовать для temporary objects
именно потому, что они умрут при выходе из конструктора (что аналогично случаю с f)
ну а b дожил до конца, как и следовало
LispGovno 03.12.2012 18:47 # 0
defecate-plusplus 03.12.2012 18:51 # +1
при выходе из функции
LispGovno 03.12.2012 18:58 # 0
defecate-plusplus 03.12.2012 19:05 # +2
глаза изначально увидели f(T()), что, понятное дело, валидно
думаю, что f(std::cref(T())) - примерно тот же случай, что и const T& a = std::cref(T());
т.е. должно быть плохо
з.ы. ну и gcc-4.7 со мной согласен
: error: use of deleted function ‘void std::cref(const _Tp&&) [with _Tp = T]’
LispGovno 03.12.2012 21:41 # 0
: error: use of deleted function ‘void std::cref(const _Tp&&) [with _Tp = T]’
Это радует. Очень хорошо. Но в стандарте я такой перегрузки не видел (им бы поправить его).
Даже здесь её нет:
http://en.cppreference.com/w/cpp/utility/functional/ref
Кстати, вот себя delete наконец положительно проявил.
defecate-plusplus 03.12.2012 21:57 # 0
defecate-plusplus 03.12.2012 22:15 # +1
http://en.cppreference.com/w/cpp/utility/functional/reference_wrapper/reference_wrapper
LispGovno 03.12.2012 22:38 # 0
>error: use of deleted function ‘void std::cref
стандарт:
>reference_wrapper( T&& x ) = delete;
Что-то они странно подошли к пониманию стандарта.
стандарт говорит, что удаляет конструктор перемещения, когда гцц говорит, что удалена функция цреф от рвалуессылки.
LispGovno 03.12.2012 22:41 # 0
LispGovno 03.12.2012 18:49 # 0
http://ideone.com/J1LvwT
LispGovno 03.12.2012 18:56 # 0
f(a*5+r); Получается по стандарту до конца функции f должен выжить только объект t в следующем псевдокоде после раскрытия? а остальные ссылки сохраненные внутри объектов окажутся дохлыми?
defecate-plusplus 03.12.2012 18:59 # +1
это всё есть в [class.temporary]
LispGovno 03.12.2012 19:07 # +1
В (std::cref(T())) - cref такая же функция, как operator* в (T()*5)
Это значит, что в обоих случаях T() должно умереть (а во втором случае ещё и объект сконструированный из 5ки, если он был) во время передачи результата следующему надвыражению, например в функцию f.
зы:
Я всегда буду обновлять тред перед постингом.
Я всегда буду обновлять тред перед постингом.
Я всегда буду обновлять тред перед постингом.
Я всегда буду обновлять тред перед постингом.
Ответили выше
defecate-plusplus 03.12.2012 19:09 # +1
глянул мельком код в ОП
глянул выхлоп
суть, что там cref в параметрах f, не увидел, поэтому ничего не заподозрил - ну и дальше рассуждал, что там просто f(T())
> Я всегда буду обновлять тред перед постингом.
только это не удобно нихера
LispGovno 03.12.2012 23:25 # 0
Мне казалось, что раньше я в ней был уверен, но теперь совершенно не уверен:
Имею ли я в данном случае передать а по ссылке или по выходу из функции а может по стандарту издохнуть и ссылка будет указывать на мусор?
LispGovno 03.12.2012 23:36 # 0
http://ideone.com/3hOQ63
Но что на эту тему говорит стандарт?
LispGovno 03.12.2012 23:51 # −1
Вобщем ответ на мой вопрос:
Печально известный способ оптимизации функций пробрасывания ссылки сквозь ссылку: - может приводить к UB. Заглядывание в стандарт не понадобилось.
Fai 03.12.2012 20:17 # −3
Стырил бормандовскую фишку, гад.
LispGovno 04.12.2012 07:38 # −1
Я всегда буду обновлять тред перед постингом.(с)
bormand 04.12.2012 08:21 # +4
Лишь бы ее не уродовали псевдознаком копирайта, составленным из скобок и буквы с.
Lure Of Chaos 04.12.2012 09:51 # +5
absolut 08.12.2012 09:18 # +1
Govnocoder#0xFF 03.12.2012 19:37 # +3
LispGovno 03.12.2012 19:45 # 0
LispGovno 03.12.2012 19:56 # −1
http://liveworkspace.org/
(онлайн компилятор крестов самый свежий и буст)
Может куда переехал?
defecate-plusplus 03.12.2012 20:32 # +1
но он вообще давно просрал все обещанные сроки
LispGovno 03.12.2012 20:39 # −1
defecate-plusplus 03.12.2012 20:49 # +1
http://www.gamedev.ru/flame/forum/?id=169251
LispGovno 03.12.2012 22:42 # −1
Fai 03.12.2012 23:43 # +1
LispGovno 04.12.2012 00:01 # −1
>ideone? Или обязательно нужен буст?
Ты не поверишь:
http://ideone.com/JsvfGK
Fai 04.12.2012 01:44 # 0
Fai 04.12.2012 01:56 # +1
http://codepad.org/ <- слишком простой
https://compilr.com/ <- нормальный
http://krillapps.com/coderunner/ <- хороший
LispGovno 06.12.2012 09:22 # +1
(покидать рабочее пространство)
Если честно, не нужен. Лайвворкспейс 1.0 был прост как пробка и всегда самый новый. За это он мне и нравился.
Если они введут мудню с регистрацией, управлением файловой системой и проектами, то это будет не приятно. Придется с него уйти.
defecate-plusplus 06.12.2012 09:30 # +3
верно
ни строчки врагу!
bormand 06.12.2012 12:46 # 0
defecate-plusplus 06.12.2012 14:47 # 0
у меня даже логина туда нет
inkanus-gray 08.12.2012 09:23 # +1
А на некоторых сайтах типа ВК просмотр подвала стал задачей нетривиальной...
LispGovno 04.12.2012 00:10 # 0
В кресты перенесут Loki::TypeList
http://gcc.gnu.org/onlinedocs/gcc-4.7.2/libstdc++/api/a00905.html
А ещё начинают готовить рефлекшен:
Получение списка всех базовых классов класса во время кококомпиляции (интересно, как это реализовано, наверное вшили в компиль):
http://gcc.gnu.org/onlinedocs/gcc-4.7.2/libstdc++/api/a00907.html
зы:Так и есть, вшили, скукота:
http://gcc.gnu.org/onlinedocs/gcc-4.7.2/libstdc++/api/a01526_source.html
AliceGoth 04.12.2012 22:09 # +2
AliceGoth 04.12.2012 22:36 # +2
T& f(const T& fa)
{
static int i=0;
cout<<"fa.a= "<<fa.a<<" i="<<i<<endl;
while(i++<=10){
f((T&)fa);
}
return (T&)fa;
}
LispGovno 05.12.2012 01:08 # 0
ты что-то этим кодом хотел про демон монстрировать?
AliceGoth 05.12.2012 01:56 # −3
ideone_eJDor1.cpp:9:14: error: expected �,’ or �...’ before �&&’ token
ideone_eJDor1.cpp:9:18: error: invalid constructor; you probably meant �T (const T&)’
ideone_eJDor1.cpp:14:31: error: expected �,’ or �...’ before �&&’ token
inkanus-gray 05.12.2012 06:33 # 0
AliceGoth 05.12.2012 13:12 # 0
bormand 05.12.2012 15:05 # +4
P.S. Если нормально скопировать сообщения не получается, сделай export LC_MESSAGES=C перед стартом gcc, чтобы он писал по-английски. Решается эта проблема добавлением опции -std=c++0x, т.к. код юзает фишки нового крестостандарта.
bormand 05.12.2012 13:20 # 0
P.S. Что-за мусор в непонятной кодировке у AliceGoth я не понял...
inkanus-gray 08.12.2012 09:27 # 0
Кстати, как у других компиляторов с указанием параметров сборки в исходнике?
defecate-plusplus 08.12.2012 09:53 # 0
у гцц такого нет, что печально
у clang, судя по всему, есть
bormand 08.12.2012 10:23 # 0
Да было бы о чем печалиться... имхо это очень сомнительная фича.
Опции будут рассеяны по нескольким местам - часть в сборочной системе, часть в исходнике. До кучи кто-нибудь додумается добавить эту прагму в хидер (удобно же чтобы либа цеплялась сразу, когда заинклудили относящийся к ней хидер).
В результате вместо одного взгляда на командную строку компилятора/компоновщика придется потратить кучу усилий на копание в коде и всех его инклудах...
defecate-plusplus 08.12.2012 10:35 # 0
Компиляция...
outer.cpp
Linking to lib file: boost_thread-vc90-mt-1_49.lib
Linking to lib file: boost_date_time-vc90-mt-1_49.lib
Linking to lib file: boost_system-vc90-mt-1_49.lib
Linking to lib file: boost_regex-vc90-mt-1_49.lib
Linking to lib file: boost_filesystem-vc90-mt-1_49.lib
Linking to lib file: boost_chrono-vc90-mt-1_49.lib
Linking to lib file: boost_program_options-vc90-mt-1_49.lib
Linking to lib file: boost_iostreams-vc90-mt-1_49.lib
Linking to lib file: boost_zlib-vc90-mt-1_49.lib
...
тяжело для каждого проекта индивидуально настраивать весь этот список
и ведь дело не в том, что именно тебе ненужно, дело в том что другим нужно, а гцц не умеет
с другой стороны, между компилятором и линкером должна быть налажена связь - каким образом передать собранный компилятором список библиотек для линковки, и, скорее всего, это и есть настоящая причина, почему гцц не умеет
bormand 08.12.2012 11:17 # +1
Да, походу причина именно в этом. Компилятор и линкер того же watcom'а и msvc рассчитаны на работу с тулзами из своего комплекта, и скорее всего не смогут съесть список либ, записанный в объектник, подготовленный чужим компилером.
В gcc же, видимо, не захотели привязываться к своему линкеру (хотя для link-time оптимизации, емнип, это все равно приходится делать), а чтобы при переключении на другой линкер (тот же ld) не возникало неведомых багов, пришлось отказаться от передачи инфы для него через объектники.
P.S. Кстати еще одна причина, наверное, заключается в привередливости гнутого линкера к порядку, в котором перечисляются библиотеки.
guest 08.12.2012 12:34 # +1
bormand 08.12.2012 10:08 # 0
Не нужно.
В любом более-менее сложном проекте есть зависимости от каких-нибудь внешних либ. И если имя либы можно вписать в прагму, то полный путь к ней - ни в коем случае.
Вторая проблема - далеко не все опции компилятора относятся к самому исходнику. Большая часть относится к текущей сборочной конфигурации, которых как правило несколько (например debug и release).
Поэтому, имхо, такая инструкция была бы полезной разве что для лаб и прочей игрушечной фигни из одного файла.
defecate-plusplus 08.12.2012 10:19 # +1
а для debug/release обычно хватает настройки выходной директории солюшена
bormand 08.12.2012 10:53 # 0
Почему в бусте такая схема выгоднее? А потому, что путь к его либам и хидерам прописывается один раз, а независимых либ в нем относительно много, и из них нужно подключить пяток-десяток.
Если же прицеплять типичную мелкую либу, собранную в отдельном каталоге - там профита от авто-линковки практически не будет.
guest 08.12.2012 12:39 # +1
Крестокомпилятор ваткома можно ещё одним добрым словом вспомнить: он поддерживает std::map на SkipList. А такой мог работать даже в многопоточной среде без локов. Насчет сравнения его производительности с RB-tree не знаю, но теже O(log n) по алгоритмической сложности.
guest 08.12.2012 16:55 # +1
LispGovno 07.12.2012 15:15 # −1
http://ideone.com/2xrCnR
LispGovno 07.12.2012 15:47 # 0
http://ideone.com/1B0Acb
Но почему виртуальность деструктора ни на что не повлияла? Неужели соптимизировал?
Также моя зайка Алёночка
http://alenacpp.blogspot.ru/2008/01/const.html
говорит, что
В данном конкретном куске кода ничего плохого я конечно не вижу.
defecate-plusplus 07.12.2012 16:18 # +3
нет, оптимизация тут не причем
надо смотреть реализацию shared_ptr в гцц, потому что с голым указателем и delete работает как положено - виртуальность имеет значение
вот тут http://en.cppreference.com/w/cpp/memory/shared_ptr/shared_ptr написано, что конструктор (2) использует delete expression as deleter, что может означать
а) будет честный delete inner_ptr_; как Base (чего мы не видим), и
б) deleter сформируется уже на этапе конструктора, и т.к. известен Y, то и delete сформируется как родной по Y * (и походу, так и есть)
LispGovno 07.12.2012 16:26 # 0
defecate-plusplus 07.12.2012 16:36 # +1
ничего странного
был создан временный объект T
должен быть удален временный объект T
а то, что его задерживает ссылка родительского типа, компилятору не важно - имеет право, пусть задерживает
LispGovno 07.12.2012 16:39 # 0
LispGovno 07.12.2012 16:30 # 0
http://ideone.com/mMioMv