Size: a a a

2020 June 26

SE

Stanislav Ershov in pro.cxx
Александр Караев
Хочу перейти с виртуального интерфейса на статический. Если упрощенно, то вместо:

struct I { virtual void foo() { /* nothing */ } };
struct A : I { void foo() final { /* impl */ } };
struct B : I { /* no foo */ };


Иметь

struct A { void foo() { /* impl */ } };
struct B { /* no foo */ };


Я могу отличить A от B, проверив статически наличие void foo(), но есть нюанс - нет аналога final/override. То есть, если я ошибусь в сигнатуре функции или опечатаюсь в названии, компилятор меня не поправит. Есть способ решить эту проблему? Я думал в сторону каких-нибудь варнингов, которые будут реагировать на неиспользуемый метод. Компилятор - gcc.
придется ждать метаклассы)
https://www.youtube.com/watch?v=drt3yXI-fqk
источник

АК

Александр Караев... in pro.cxx
а как метаклассы решат проблему?
статические проверки и сейчас можно сделать
источник

VS

Vlad Serebrennikov in pro.cxx
Andrey здравствуйте. В очередной раз хочу поднять тему нулевого указателя.
Примеры кода, поведение которых хотелось бы у вас прояснить (по возможности со ссылками на стандарт):
A *p{nullptr};
*p; // 1
std::cout << (*p, 5); // 2
A a{*p}; // 3
p->non_static_mem_fn(); // 4
p->static_mem_fn(); // 5
источник

VS

Vlad Serebrennikov in pro.cxx
Что, кажется, удалось выяснить к настоящему моменту:
Пример 1
Согласно expr.unary.op.1, разыменование возвращает an lvalue referring to the object or function to which the expression points. Есть трактовка, что раз объекта нет, то UB, но, например, dangling ссылки сами по себе не UB несмотря на то, что исходного объекта нет. Еще есть довольно старая CWG issue 232, где CWG пришла к неформальному консенсусу, что p = 0; *p; is not inherently an error. Полагаю, что в этом примере UB нет.

Пример 2
Видно две потенциальные возможности UB. Разыменование освещено в предыдущем примере, поэтому здесь сфокусируюсь на операторе запятая. Согласно expr.comma.1, операнды вычисляются слева направо, и то, что вернуло разыменование, становится discarded-value выражением. Неформальный консенсус в CWG issue 232 также в том, что an lvalue-to-rvalue conversion would give it undefined behavior, но и его не происходит, потому что о volatile речь у нас нигде не идет (expr.context-2), не говоря о том, что в текущем тексте стандарта этот консенсус, кажется, тоже не отражен: в conv.lval из релевантного только the value contained in the referenced object is not accessed, что наоборот предупреждает возможность UB (basic.lval.11). Полагаю, что UB нет и здесь.

Пример 3
Полагаю, здесь UB начнется самое позднее на попытке доступа к несуществующему объекту под p внутри конструктора копирования согласно basic.lval.11.

Пример 4
Полагаю, здесь UB начнется в момент вызова функции-члена у несуществующего объекта согласно class.mfct.non-static.1.

Пример 5
Если предположить, что разыменование, которое происходит согласно 59 сноске, само по себе допустимо, то далее я не нахожу требований, чтобы сам объект существовал, и, соответственно, причин для UB.
источник

A

Alex Ф-ф-фэils!🌠︙... in pro.cxx
Александр Караев
Хочу перейти с виртуального интерфейса на статический. Если упрощенно, то вместо:

struct I { virtual void foo() { /* nothing */ } };
struct A : I { void foo() final { /* impl */ } };
struct B : I { /* no foo */ };


Иметь

struct A { void foo() { /* impl */ } };
struct B { /* no foo */ };


Я могу отличить A от B, проверив статически наличие void foo(), но есть нюанс - нет аналога final/override. То есть, если я ошибусь в сигнатуре функции или опечатаюсь в названии, компилятор меня не поправит. Есть способ решить эту проблему? Я думал в сторону каких-нибудь варнингов, которые будут реагировать на неиспользуемый метод. Компилятор - gcc.
Аналог финала я помню хотел как бумажку в ИСО оформить
источник

CD

Constantine Drozdov in pro.cxx
Я бы лично предложил комитету ограничиться явной формулировкой, что ссылка в момент формирования должна указывать на объект соответствующего типа
источник

CD

Constantine Drozdov in pro.cxx
Я не понимаю ни одного случая, когда в разумных целях нужно нарушать это правило
источник

VS

Vlad Serebrennikov in pro.cxx
Constantine Drozdov
Я бы лично предложил комитету ограничиться явной формулировкой, что ссылка в момент формирования должна указывать на объект соответствующего типа
по-моему, оно есть
dangling reference тут не с той целью упоминается
источник

CD

Constantine Drozdov in pro.cxx
Vlad Serebrennikov
по-моему, оно есть
dangling reference тут не с той целью упоминается
Но если есть, то *p в (1) это немедленно UB. *nullptr не указывает на объект какого-либо типа
источник

VS

Vlad Serebrennikov in pro.cxx
Constantine Drozdov
Но если есть, то *p в (1) это немедленно UB. *nullptr не указывает на объект какого-либо типа
ссылки идут как пример lvalue, которые могут не указывать на объект
источник

CD

Constantine Drozdov in pro.cxx
Vlad Serebrennikov
ссылки идут как пример lvalue, которые могут не указывать на объект
Они могут не указывать, но не в момент формирования, я же это и пишу.
источник

CD

Constantine Drozdov in pro.cxx
Мы не можем обеспечить ссылочный контроль, но нет никакой причины разрешать формальное разыменование просто потому, что это операция "ничего не сделать"
источник

CD

Constantine Drozdov in pro.cxx
В частности, если разыменование это операция "ничего не сделать", мы только что стандартизировали весь ABI ссылок
источник

VS

Vlad Serebrennikov in pro.cxx
Constantine Drozdov
Они могут не указывать, но не в момент формирования, я же это и пишу.
я предлагаю не уходить от темы в ссылки, которые лишь частный случай lvalue
источник

CD

Constantine Drozdov in pro.cxx
Vlad Serebrennikov
я предлагаю не уходить от темы в ссылки, которые лишь частный случай lvalue
мне кажется, что последствием ни к чему не обязывающего разыменования немедленно становится эквивалентность ссылок и указателей в ABI
источник

CD

Constantine Drozdov in pro.cxx
мы можем инициализировать ссылку любым указателем, а любой указатель преобразовать в ссылку
источник

VS

Vlad Serebrennikov in pro.cxx
Constantine Drozdov
мне кажется, что последствием ни к чему не обязывающего разыменования немедленно становится эквивалентность ссылок и указателей в ABI
а ссылки и так указатели в itanium abi, насколько я помню
источник

CD

Constantine Drozdov in pro.cxx
Vlad Serebrennikov
а ссылки и так указатели в itanium abi, насколько я помню
это undefined для стандарта
источник

CD

Constantine Drozdov in pro.cxx
struct A { int * p; };
struct B { int & p; };
static_assert(sizeof(A) == sizeof(B));
источник

VS

Vlad Serebrennikov in pro.cxx
Constantine Drozdov
мне кажется, что последствием ни к чему не обязывающего разыменования немедленно становится эквивалентность ссылок и указателей в ABI
может быть
но я очень не хочу, чтобы мы сейчас ушли в эту частность
источник