Создание методов на основе существующих в Scada

Стартовая страница Форумы Разработка и интеграция Создание методов на основе существующих в Scada

Просмотр 13 сообщений - с 1 по 13 (из 13 всего)
  • Автор
    Записи
  • #12510
    manjey73
    Участник

    Собственно вопрос, как создать метод в своем коде, используя методы, реализованные в Scada для сокращения вводимых переменных, а главное для расширения функционала.

    Интересует в первую очередь метод Read из Connection ?

    #12512
    Taw
    Участник

    1) extension methods
    2) override, virtual methods, constructors, polymorphism, inheritance
    3) Delegate,new Delegate which based on the others

    #12517
    manjey73
    Участник

    Taw а теперь не совсем для программистов 🙂
    кусочки кода можно ?
    Вот тут и так мы открываем, тут дублируем переменные основного метода, тут рыбу заворачиваем, а вот тут надо свой код написать.

    з.ы. я конечно поищу по ключевым словам, что вы указали, но когда искал решения своих задач то столкнулся с тем, что даже на msdn примеры очень и очень примитивные и потом тратил время на метод тыка….

    #12519
    Mikhail
    Модератор

    В классе Kp***Logic заводите свой метод, в котором вызываете стандартный метод:

    private void MyRead(ваши аргументы метода)
    {
      Connection.Read(...);
    }

    Обычно буфер для чтения данных Вам уже будет доступен в методе MyRead, т.к. он объявлен на уровне класса логики. Какие входящие аргументы будут в MyRead и возвращаемое значение, зависит от конкретного случая. Смысл в том, чтобы в методе MyRead было меньше параметров, чем в Connection.Read для удобства.

    #12528
    manjey73
    Участник

    Спасибо, попробую…

    #12533
    manjey73
    Участник

    private void ReadBinStop (……… , out bool stopReceived, ……)
    {

    }

    Ругается на out — До передачи управления из текущего метода параметру, помеченному ключевым словом out, «stopReceived» должно быть присвоено значение.

    Если в изначальном методе есть out, как его же передать потом в своем ?
    Ну мне не столько удобство, сколько добавить функционал, которым не хочется перегружать, хотя что там перегружать, если по умолчанию будет 0 🙂

    з.ы. не знаю, заработает ли, но попробую…..

    Михаил, просто попутный вопрос, ScadaCommUpdate войдет не только в версию 5.7 но и в 5.6.1 ?

    • Ответ изменён 7 лет, 1 месяц назад пользователем manjey73.
    • Ответ изменён 7 лет, 1 месяц назад пользователем manjey73.
    #12540
    manjey73
    Участник

    В общем фигня получается, чтобы после остановки по массиву дочитать еще 2 байта CRC и склеить в одну строку выходит так…

            private int Read(byte[] buffer, int offset, int maxCount, Connection.BinStopCondition stopCond, out bool stopReceived, out string logText, int colByte = 0)
            {
                bool stopRec = false;
                string logTxt;
                int readc0 = Connection.Read(buffer, offset, maxCount, ReqParams.Timeout, stopCond, out stopRec, CommUtils.ProtocolLogFormats.Hex, out logTxt); // В данном драйвере ProtocolLogFormats - HEX
                string logTxt1 = "";
                if (stopRec)
                {
                    int readc1 = Connection.Read(buffer, readc0, colByte, ReqParams.Timeout, CommUtils.ProtocolLogFormats.Hex, out logTxt1);
                    int itxt = logTxt1.IndexOf(":");
                    logTxt1 = logTxt1.Substring(itxt + 1);
                    string cnt = Convert.ToString(readc0);
                    int ic0 = logTxt.IndexOf(cnt);
                    readc0 = readc0 + readc1;
                    logTxt = logTxt.Remove(ic0, cnt.Length);
                    logTxt = logTxt.Insert(ic0, Convert.ToString(readc0));
                }
                stopReceived = stopRec;
                logText = String.Concat(logTxt, logTxt1);
                return readc0;
            }
    

    Если бы дочитка нужного количества байт была внутри в недрах, то там пара строк кода и мы получаем на выходе сразу
    Приём (35): FF FF 10 01 0A 02 10 1F 03 53 36 39 10 02 09 31 09 33 35 31 0C 09 30 09 83 8A A0 AB 2F E7 0C 10 03 BF B3

    а тут приходится извращаться… может есть способ быстрее ?
    Единственное из полезностей, так это сокращения записи вызова уже потом в коде, чтобы не печатать многа букав…

    • Ответ изменён 7 лет, 1 месяц назад пользователем manjey73.
    #12544
    manjey73
    Участник

    Тормоз, можно же проще еще раз выполнить Connection.BuildReadLogText

            private int Read(byte[] buffer, int offset, int maxCount, Connection.BinStopCondition stopCond, out bool stopReceived, out string logText, int colByte = 0)
            {
                bool stopRec;
                string logTxt;
                int readc0 = Connection.Read(buffer, offset, maxCount, ReqParams.Timeout, stopCond, out stopRec, CommUtils.ProtocolLogFormats.Hex, out logTxt); // В данном драйвере ProtocolLogFormats - HEX
                if (stopRec)
                {
                    int readc1 = Connection.Read(buffer, readc0, colByte, ReqParams.Timeout, CommUtils.ProtocolLogFormats.Hex, out logTxt);
                    readc0 = readc0 + readc1;
                }
                stopReceived = stopRec;
                logText = Connection.BuildReadLogText(buf_in, 0, readc0, CommUtils.ProtocolLogFormats.Hex);
                return readc0;
            }
    
    • Ответ изменён 7 лет, 1 месяц назад пользователем manjey73.
    • Ответ изменён 7 лет, 1 месяц назад пользователем manjey73.
    #12560
    Mikhail
    Модератор

    Последний вариант выглядит аккуратно. Работает?
    Немного оптимизировать: вызывать BuildReadLogText только в той ветке кода, в которой дочитывался хвост пакета, а иначе logText уже итак определён.

    #12565
    manjey73
    Участник

    Блин, дык я о чем и толковал. Конец пакета это CRC, поймать ее не представляется возможным, ибо она всегда меняется. Длины пакета в пакете не фигурирует от слова совсем.
    Данные в пакете в виде ASCII символов. то есть значение 33,42 это в байтах
    33 33 2E 34 32 (2E вроде заместо точки), разделители данных 09 — символ табуляции.
    И еще такой же прикольный счетчик запрос — ответ в виде ASCII от 0 до 99, соответственно счетчик может быть одним байтом 38 (номер 8) а может быть двумя байтами 35 37 (57). То есть длина как запроса так и ответа в принципе может отличаться на 1 байт. Ну и как при таком подходе высчитать длину ответа ?
    Зато в конце пакета всегда один набор массива байт + 2 байта CRC.

    Разбивая на 2 запроса, даже не наводя красоту, получается

    чтение с остановкой
    формирование строки лога (сидит в функции чтения)
    вывод строки лога
    чтение еще раз 2-х байт CRC
    формирование строки лога
    вывод строки лога

    6 процедур фактически. я предлагал сделать дочитывание байт CRC сразу в функции ScadaCommCommon, тогда получилось бы

    чтение с остановкой
    добавочное чтение нужного количества байт
    формирование строки лога
    вывод лога

    4 процедуры.. Количество байт после остановки сделать по умолчанию 0,
    думаю при 0 байт после остановки на скорости никак не скажется. И совместимость никак не пострадает, так как параметр имеет значение по умолчанию. А при необходимости всегда можно продолжить чтение нужного количества байт…
    При чем в плане совместимости не пострадает, даже если добавить параметр по умолчанию и в функцию остановки по одному байту, а не по массиву.

    • Ответ изменён 7 лет, 1 месяц назад пользователем manjey73.
    #12567
    Taw
    Участник

    1) Это когда вы не имеете доступа к исходникам, допустим dll или не хотите лезть в исходники. Вы просто добавляете свой метод к остальным методам класса. Имеете доступ ко всем остальным методам и полям класса и добавляете свой метод для класса, исходный код которого недоступен.
    2) Полиморфизм. Допустим есть набор фигур, фигуры имеют какие то общие методы, допустим вычисление стороны по ее координатам вершин. И в тоже время есть методы которые вычисляют периметр и площадь. Но эти методы отличаются для каждой из фигур. Но вы можете их вызвать в обычном цикле перебора фигур (по коллекции или массиву базового класса). Вы добавляете свою фигуру, берете за предка класс (обычно абстрактный типа фигура) и все его методы. И добавляете свои методы. Но все методы предка класса доступны. Это можно через виртуальные методы и интерфейсы.
    3) Это в С++ как указатель на функцию. Т.е. вы можете в качестве аргументов метода использовать другие методы.

    #12570
    manjey73
    Участник

    Taw ну так я и не хочу лезть в исходники, система то может меняться, и каждый раз добавлять будет некрасиво. Тем более это нужно для работы драйвера устройства. У меня тоже нет времени постоянно и каждый раз их поддерживать. Может быть другая работа и просто будет некогда.
    Михаилу огромное спасибо за добавление функции остановки чтения пакета по массиву байт. Так как именно там реализация более правильная с логической точки зрения.
    А это уже маленькие штрихи для красоты, но которые вроде как логически тоже более правильные внутри ядра. 🙂

    #12579
    Mikhail
    Модератор

    Чтобы применить классическое ООП, Rapid SCADA должна поддерживать создание собственных каналов связи на основе существующих и подключение их к Коммуникатору по аналогии с драйверами. Это возможно реализовать, но пока что не видно востребованности данной функции.

Просмотр 13 сообщений - с 1 по 13 (из 13 всего)
  • Для ответа в этой теме необходимо авторизоваться.