Преобразование интегрального значения к типу структуры при инициализации
От: Евгений Музыченко Франция https://software.muzychenko.net/ru
Дата: 20.08.18 18:32
Оценка:
Есть функция, возвращающая 32-разрядное интегральное значение (int, long и т.п.), и определена упакованная структура того же размере (например, два short). Присвоить значение переменной структуры несложно, достаточно лишь взять указатель на структуру, преобразовать его в указатель интегрального типа, и разыменовать.

Хочется таким же манером (в одно действие) инициализировать переменную структуры. Но MS VC++ 15.00 и 19.10 напрочь отказывается преобразовывать интегральное значение к типу структуры, ссылаясь на отсутствие подходящего конструктора. Удается вывернуться лишь взятием и преобразованием указателя на функцию, с вызовом ее через этот указатель.

Есть ли возможность преобразовать тип при инициализации более кошерными методами?
struct initialization cast type integral
Re: Преобразование интегрального значения к типу структуры при инициализации
От: watchmaker  
Дата: 20.08.18 19:28
Оценка:
Здравствуйте, Евгений Музыченко, Вы писали:

ЕМ>Есть функция, возвращающая 32-разрядное интегральное значение (int, long и т.п.), и определена упакованная структура того же размере (например, два short).


ЕМ>Присвоить значение переменной структуры несложно, достаточно лишь взять указатель на структуру, преобразовать его в указатель интегрального типа, и разыменовать.

Тем самым на ровном месте нарушив strict aliasing rule и сделав поведение программы неопределённым. Очень плохой способ! Используй std::bit_cast или реализуй его аналог через memcpy.


ЕМ>Есть ли возможность преобразовать тип при инициализации более кошерными методами?

Написать и предоставить конструктор, разумеется :)
Re[2]: Преобразование интегрального значения к типу структуры при инициализации
От: Евгений Музыченко Франция https://software.muzychenko.net/ru
Дата: 20.08.18 19:38
Оценка: :)
Здравствуйте, watchmaker, Вы писали:

W>Тем самым на ровном месте нарушив strict aliasing rule и сделав поведение программы неопределённым.


Я Вас умоляю! Это используется во множестве программ, и прекрасно контролируется. Когда я стану делать программы для заранее неизвестного железа и компилятора — буду этим заморачиваться, но не сейчас.

W>Написать и предоставить конструктор, разумеется


Структуры определены не мной. Можно, конечно, создать производный/отдельный тип и определить для него конструктор, но это уже как-то громоздко.
Re[3]: Преобразование интегрального значения к типу структур
От: SomeOne_TT  
Дата: 20.08.18 19:53
Оценка:
ЕМ>Структуры определены не мной. Можно, конечно, создать производный/отдельный тип и определить для него конструктор, но это уже как-то громоздко.

Громоздко, да


#include "stdafx.h"


struct Shorts
{
    short one;
    short two;
};

class ShortsConvert
{
    ShortsConvert(unsigned int source)
    {
        s_.int_field = source;
    }
    ShortsConvert(const Shorts& source)
    {
        s_.shorts_field = source;
    }

    operator unsigned int() const { return s_.int_field; };
    operator Shorts() const { return s_.shorts_field; };
private:
    union ShortsUnion
    {
        unsigned int int_field;
        Shorts shorts_field;
    };

    ShortsUnion s_;
};


int main()
{
    Shorts s{ 5,1 };
    unsigned int i = (ShortsConvert)s;
    Shorts shorts = (ShortsConvert)i;
   return 0;
}
Отредактировано 20.08.2018 20:10 SomeOne_TT . Предыдущая версия . Еще …
Отредактировано 20.08.2018 19:54 SomeOne_TT . Предыдущая версия .
Re[3]: Преобразование интегрального значения к типу структуры при инициализации
От: N. I.  
Дата: 20.08.18 20:19
Оценка:
Евгений Музыченко:

W>>Написать и предоставить конструктор, разумеется


ЕМ>Структуры определены не мной. Можно, конечно, создать производный/отдельный тип и определить для него конструктор, но это уже как-то громоздко.


Можно просто сделать отдельные функции для преобразования туда и обратно. Внутри сможешь использовать хоть гарантированно рабочие решения, хоть хаки, потом можно будет поправить в случае чего.

https://wandbox.org/permlink/VWyz6pf5gxXiXSeJ
Re: Преобразование интегрального значения к типу структуры п
От: rg45 СССР  
Дата: 21.08.18 09:23
Оценка: +1
Здравствуйте, Евгений Музыченко, Вы писали:

ЕМ>Хочется таким же манером (в одно действие) инициализировать переменную структуры. Но MS VC++ 15.00 и 19.10 напрочь отказывается преобразовывать интегральное значение к типу структуры, ссылаясь на отсутствие подходящего конструктора.


Все прекрасно преобразуется и безо всяких кастомных конструкторов:

https://ideone.com/uorCOR

struct pair_of_short
{
  short first, second;
};

const pair_of_short p = reinterpret_cast<const pair_of_short&>(static_cast<const long&>(42));


Оформи это преобразование в виде специальной функции, как советовали выше, и будет тебе счастье.
--
Не можешь достичь желаемого — пожелай достигнутого.
Отредактировано 21.08.2018 9:30 rg45 . Предыдущая версия .
Re[2]: Преобразование интегрального значения к типу структуры п
От: Евгений Музыченко Франция https://software.muzychenko.net/ru
Дата: 21.08.18 09:55
Оценка:
Здравствуйте, rg45, Вы писали:

R>
R>const pair_of_short p = reinterpret_cast<const pair_of_short&>(static_cast<const long&>(42));
R>


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