Продолжаем ковыряние в группе указателей. Теперь на очереди Variant.
VARIANT
Описание
Variant - это ссылка или указатель, который указывает на тэги различных типов данных. Он не может указывать на конкретный экземпляр, ну и следовательно на все что с этими экземплярами связано.
Указатель VARIANT может быть объектом элементарного типа данных, например INT или REAL. Это также может быть STRING, DTL, ARRAY из STRUCT, UDT или ARRAY из UDT. Указатель VARIANT может распознавать структуры и указывать на отдельные компоненты структуры. Операнд типа данных VARIANT не занимает места в блоке данных экземпляра или в рабочей памяти. Однако он будет занимать место в памяти ЦП.
VARIANT могут быть объявлены только для формальных параметров в блочном интерфейсе функции в разделах VAR_IN, VAR_IN_OUT и VAR_TEMP. НЕЛЬЗЯ объявить в разделе static, так как не будет известен размер объекта.
Ну и понятное дело, что мы можем там делать различные универсальные FB и FC.
ИНСТРУКЦИИ
Что же нам предлагают по функционалу к этому чудесному типу данных:
- bool EQ_Type(In1:=Variant, In2:=Variant) - ну сравнение типов на эквивалентность. В случае удачи вернет True
- bool NE_Type(In1:=Variant, In2:=Variant) - сравнение типов на не эквивалентность
- bool EQ_ElemType(In1:=Variant, In2:=Variant) - сравнение по типу элементов массива с переменной на эквивалентность.
- bool NE_ElemType(In1:=Variant, In2:=Variant) - а вот догадайся
- bool IS_NULL(Variant) - проверка пустой ли элемент. Ссылается на ZERO POINTER
- bool NOT_NULL(Variant) - проверяем что не пустой. Не сcылкается на ZERO POINTER
- bool IS_ARRAY(Variant) - проверяем что массива
- type_id TypeOf(Variant) - возвращает тип переменной
- type_id TypeOfElements(Variant) - возвращает тип элементов
- int MOVE_BLK_VARIANT(SRC := VARIANT, COUNT := UDINT, SRC_INDEX := DINT, DEST_INDEX := DINT, DEST => variant) - Инструкция MOVE_BLK_VARIANT требуется только в том случае, если вы хотите переместить части ARRAY с типом данных, который известен только во время выполнения программы. Можно использовать MOVE - для копирования всей структуры и MOVE_BLK - для копирования части массива с известным типом данных;
- VariantGet(SRC:=VARIANT, DST=>VARIANT) - читаем значение.
- VariantPut(SRC:=VARIANT, DST:=VARIANT) - Записываем значения
- udint CountOfElements(Variant) - получаем количество элементов в массиве
- И тут еще две конвертации DB_ANY -> VARIANT и VARIANT->DB_ANY
Из всего, что тут есть, мне интересно разобрать блоки MOVE, PUT/GET и немного в конвертацию. Все остальное по ходу пьесы.
КАК ЖЕ НАМ ЭТО ИСПОЛЬЗОВАТЬ?
MOVE и PUT/GET
И так что мы имеем. Обычным присваиванием ":=" мы ничего сделать не сможем.
А вот MOVE_BLK_VARIANT и VariantGet - работают исправно.
Ну и ранее описанный способ через REF я показывать не буду.
VariantPut тоже работает, но при условии того что в SRC будет конкретное значение.
А вот что касается DB_ANY_TO_VARIANT и наоборот - это чуток потом. А то какая-то обширная тема.