Re[2]: Сравнение union'ов
От: mp_op  
Дата: 11.08.11 15:10
Оценка:
Здравствуйте, Centaur, Вы писали:

C>Здравствуйте, mp_op, Вы писали:


_>>Подскажите пожалуйста, как корректно (по стандарту) сравнить два union`а гарантированно одинакового размера, но неизвестного содержания


C>Для начала следует определиться, что значит «объект a типа union A равен объекту b типа union B».

sizeof(u1) == sizeof(u2)

C>В общем случае это неосмысленное отношение.

Общий случай мне и не нужен. Вот еще раз пример, который я приводил, давайте отталкиваться от него.
union u1
{
     int *  a;
     void * v;
} v1;

union u2
{
    int *  a;
    char * b;
    void * v;
} v2;

uzhas написал, про сведение к единому типу, если почитать ветку с Pavel Dvorkin, то я там как раз это и предлагаю. Только вместо int* — void*.
В юнионах всегда только указатели и всегда присутствует void*.
Мой вопрос в следующем, корректно ли по стандарту сравнивать

v1.v == v2.v

при условии, что изначально записаны в v1 был int*, а в v2 — char*?
Равносильно ли это простому приведению к типу void*? Даже чуть больше уточню, интересует сравнение на неравенство (и только).

Я знаю, что union_cast`ы запрещены. Но знаю, что любой указатель на объект в С++ можно сконвертировать в void* неявно. Нет ли тут лазейки?

C>В частном случае, когда имена и типы полей совпадают, скорее всего, понятие равенства будет выглядеть как «в обоих объектах активен один и тот же вариант И значения этих вариантов равны», для какого-нибудь набора предикатов равенства над парами каждого варианта.

В том и дело, что какой из вариантов активен — неизвестно. Нужно просто сравнить v1 и v2. Хочу узнать корректный способ. Типы полей совпадают всегда только в одном — есть void*, все остальные могут быть произвольные указатели на объекты (только указатели). Исходя из этого все мои юнионы всегда sizeof(U) == sizeof(void*), так как получается, что void* всегда самый большой член юниона (по причине конвертируемости в него всех остальных указателей).

Немного сумбурно, но вроде сейчас больше нет недомолвок. Спасибо.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.