Добрый день.
Предположим, что необходимо получать данные по инструментам, для этого мы добавляем нужные столбцы в квике и в программе, подписываемся на событие новой записи и изменения данных в таблице Secirities и в обработчике Trader.Connected запускаем экспорт по DDE этой таблицы. Данные поступают, мы их видим как в обработчиках событий, так и в таблице Trader.Securities. Далее есть два варианта:
- в любой момент времени мы можем обратиться к данной таблице из кода стратегии и прочитать нужные нам данные;
- в обработчиках событий копировать поступившие данные в свои структуры и в стратегии работать со своими данными.
Интересует такой вот момент, во втором случае разработчик сам занимается вопросом согласованности данных, т.е. любая запись и доступ к данным заключены в блок синхронизации и в любой момент времени данные у нас согласованы. Каким образом обстоит дело в первом случае?
Комментарии (15)
Вход или Создать аккаунт, Войдите или зарегистрируйтесь, чтобы оставить комментарий
Это не так. Объекты торговых типов обновляются без какой-либо синхронизации, и не атомарно.
Т.о. получается, что когда я в событии изменения записи таблицы (SecurityChanged) копирую данные из пришедшего объекта в свою внутреннюю структуру они могут поменяться? Может имеет смысл добавить хотя SyncRoot для возможности lock-а или сделать по принципу много читателей - один писатель?
А зачем?
Мне кажется вы друг друга недопонимаете.
На мой взгляд, esper хотел спросить: являются ли свойства объекта класса QuikTrader потокобезопасными? И насколько я знаю, ответ: да, являются.
Михаил, поправьте меня, если я ошибаюсь.
Попутный уточняющий вопрос: а все ли свойства потокобезопасны? В частности интересует свойство Security.ExtensionInfo Необходима ли синхронизация этого свойства при доступе из разных потоков?
Смотря что Вы с ним хотите делать. Если просто сделать так
var info = sec.ExtensionInfo;, а если ``` sec.ExtensionInfo.Contains(key);К примеру, у меня стратегия крутится в другом потоке, на каждой итерации ей нужны данные из таблицы инструментов. Получение данных из таблицы осуществляется не в одном месте, а рассредоточено по всей функции стратегии. Я считываю одно поле для конкретного инструмента в начале функции, далее выполняю другие действия, из квика приходят новые данные, считываю другое поле для этого же инструмента и получаю несогласованные данные.
Да, нужно. Это вариант 2.
А каким образом можно сделать синхронизацию с внутренним обновлением этих данных? Чтобы пока я их читаю они не менялись?
Наверное никак, так как никакой синхронизации в обновлении данных нет. А в чем заключается сама задача?
К примеру, у меня стратегия крутится в другом потоке, на каждой итерации ей нужны данные из таблицы инструментов. Получение данных из таблицы осуществляется не в одном месте, а рассредоточено по всей функции стратегии. Я считываю одно поле для конкретного инструмента в начале функции, далее выполняю другие действия, из квика приходят новые данные, считываю другое поле для этого же инструмента и получаю несогласованные данные.
Хотелось бы иметь возможность получения согласованных данных. Сейчас просто в событиях новой записи и изменения записи копирую данные в свои структуры и работаю с ними, возможно есть вариант более правильный.
Можете эти поля указать?
Михаил, добрый день. Еще один вопрос про потоки.
Каким образом можно перебрать все элементы свойства QuikTrader.MyTrades?
Если применить к этому свойству foreach, то в процессе работы цикла к этому свойству из другого потока могут добавится новые элементы и foreach может сработать некорректно(может пропустить некоторые элементы).
Соответственно, что бы применить foreach к QuikTrader.MyTrades, нужно на время выполнения этого цикла блокировать изменение этого свойства. Есть ли такая возможность? Например, публичный объект для блокировки?
Или есть другой способ выполнить задачу?
Напрямую. Всегда возвращается копия данных, которая не модифицируется.
Попробуйте так сделать. Ошибка будет совсем другая.
Предлагаю рассматривать задачу с практической стороны. Скажите, зачем вам это нужно на конкретном примере, и я попробую найти путь.
В принципе это то, что было надо. И то, чего я не знал. Практическую задачу я вроде в комментарии и описал: нужно было быть уверенным, что пока перебираешь все элементы свойства, это свойство не изменится. Спасибо за ответ.
Итак, насколько я понял если во время выполнения следующего кода из Квика придет новая моя сделка, то она в цикл никак не попадет?
Возможно, что бы сто раз одно и то же не объяснять, стоит добавить в документацию раздел с описанием того, что в библиотеке потокобезопасно, а что нет. Хотя понимаю, что на все надо время.