Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

реализация из Delphi в C#

19K
24 ноября 2009 года
WantToProg
63 / / 19.01.2009
Помогите реализовать одну процедурку. C# только учу, интересно как сделать.

 
Код:
buff: array[1..1024] of char;
function T_Socket.RecvData: String;
var res: Integer;
var i: String
begin
iRecv := Recv(Sock, buff, sizeOf(buff), 0)
end;


Суть в том, что эта обработка принимает последовательно набор символов от клиента. И отправляет им ответ в зависимости от условия, предоставленного ниже.
У меня есть сервер, такого типа:

Код:
TcpListener listener = new TcpListener(IPAddress.Any, 9101);
            listener.Start();
            while(true)
            {
            using (TcpClient c = listener.AcceptTcpClient())
            using (NetworkStream n = c.GetStream())            
            {
                MessageBox.Show("connected");
               
                char msg = new BinaryReader(n).ReadChar();

                strmsg = Convert.ToString(msg);

                MessageBox.Show(strmsg);
                for (i = 0; i < data.Count(); i++)
                    if (data == strmsg)
                    {
                        int k = i + 2;
                        strmsg = data[k] + data[k + 1];
                        BinaryWriter w = new BinaryWriter(n);
                        msg = Convert.ToChar(w);
                        w.Write(msg);
                        w.Flush();
                    }
            }

            }
            listener.Stop();


Что то я подзапарился над конвертацией в форматы, то что выше (BinaryReader(n).ReadChar()) читает во первых только один символ, а во вторых вылетает при попытке писать char в порт клиента(w.Write(msg)).

data - набор данных типа List<string>
5
24 ноября 2009 года
hardcase
4.5K / / 09.08.2005
Код:
Encoding encoding = Encoding.GetEncoding(1251);  // кодировка символов сетевого потока -
                                                 //  однобайтовая кириллическая

TcpListener listener = new TcpListener(IPAddress.Any, 9101);
listener.Start();
while(true) {
    using (TcpClient client = listener.AcceptTcpClient())
    using (NetworkStream stream = client.GetStream())
    using (StreamReader reader = new StreamReader(stream, encoding))
    using (StreamWriter writer = new StreamWriter(stream, encoding)) {
        MessageBox.Show("connected");

        // сколько данных читать?
        string input = reader.ReadLine(); // читает строку до следующего Environment.NewLine
                                          // и пропускает его
       
        // пример записи List<string> data в сетевой поток
        foreach(string line in data) {
            if(input == line) {
                writer.WriteLine("You selected: " + input);
            } else {
                // writer.Write(line); // без Environment.NewLine
                writer.WriteLine(line);  // добавляет Environment.NewLine
            }
        }
        writer.Flush(); // сбрасываем данные из внутреннего буфера StreamWriter
                        // в сетевой поток
                       
        // <-- тут соединение разорвется
    }
}
listener.Stop();
19K
24 ноября 2009 года
WantToProg
63 / / 19.01.2009
 
Код:
// сколько данных читать?
        string input = reader.ReadLine(); // читает строку до следующего Environment.NewLine
                                          // и пропускает его


В том то вся и проблема, что неизвестно сколько данных читать.
И я не могу даже понять, считывает он что то или нет :(

В случае с BinaryReader.ReadChar считывает только первый символ, но покрайней мере, хоть что то считывает

Про StreamReader прочитал такую вещь.
Цитата:
Если вы используете потом StreamReader, то рискуете остановить работу на неопределенное время, потому что у потока NetworkStream конца нет.
Класс StreamReader может выйти из под контроля при работе с потоком NetworkStream, даже если вы собираетесь вызывать только ReadLine. Причина в том, что у класса StreamReader имеется буфер предварительного чтения, и дело может закончится попыткой прочитать больше байтов, чем доступно в настоящий момент и приостановкой работы на неопределенное время.


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

PS: И еще. Только что обнаружил. Первое сообщение доходит только тогда, когда поступает второе. Причем после этого, происходит отключение клиента. Что то я недопонимаю...

5
24 ноября 2009 года
hardcase
4.5K / / 09.08.2005
Цитата: WantToProg

Про StreamReader прочитал такую вещь.

Все это говорит лишь о том, что лучше воздержаться от использования ReadLine в production-коде.

Цитата: WantToProg

По этой причине, я не рискнул создавать таким образом.

Вводится собственный контроль длины считываемой строки ;)

Цитата: WantToProg
Может есть какое нибудь другое решение?

Для начала я предложу вам разобраться с протоколом, на котором вы хотите организовать взаимодействие:

Цитата: WantToProg

В том то вся и проблема, что неизвестно сколько данных читать.

Вот и займитесь этим вопросом. Не зная что за данные вам приходят вы не сможете с ними работать.


Цитата: WantToProg
Первое сообщение доходит только тогда, когда поступает второе. Причем после этого, происходит отключение клиента. Что то я недопонимаю...


В сети данные ходят пакетами, отталкивайтесь от этого.


Для отладки сетевых приложений есть как мощные снифферы вроде WireShark или MS NetworkMonitor, так и элементарнейшая утиллита командной строки telnet (попробуйте ее).

19K
24 ноября 2009 года
WantToProg
63 / / 19.01.2009
Цитата:
Вводится собственный контроль длины считываемой строки


Для начала я предложу вам разобраться с протоколом, на котором вы хотите организовать взаимодействие:

Вот и займитесь этим вопросом. Не зная что за данные вам приходят вы не сможете с ними работать.

В сети данные ходят пакетами, отталкивайтесь от этого.



Каким образом выполнить контроль? Я знаю, что ко мне, т.е. к серверу приходят сообщения типа:
46064226
2000131467848
20 589
но они разной длинны, и возможности сделать их одинаковыми нет.
Взаимодействие по протоколу tcp/ip, клиента я к сожалению конфигурировать не могу.
Но даже если в сети и ходят данные пакетами, как все таки сделать так, чтоб клиент не отключался после отправки сообщения?
И все таки, почему первое сообщение приходит после отправки второго?

5
24 ноября 2009 года
hardcase
4.5K / / 09.08.2005
Когда вы наконец поймете (и расскажете тут), какой же длины сообщения:
Цитата: WantToProg

к серверу приходят сообщения типа:
46064226
2000131467848
20 589

то сможете ответить на вопрос

Цитата: WantToProg
Каким образом выполнить контроль?



Цитата: WantToProg

Взаимодействие по протоколу tcp/ip, клиента я к сожалению конфигурировать не могу.

TCP/IP - это транспортный протокол, я же спрашиваю про протокол прикладного уровня, т.е. соглашения о передаче данных между программами. Простой аналог: HTTP - это текстовый (ну, не совсем, конечно) протокол прикладного уровня.


Цитата: WantToProg
как все таки сделать так, чтоб клиент не отключался после отправки сообщения?

Клиент отключается сам?


Я уже в третий раз спрашиваю, как обмен данных происходит, пока вы не поймете этого, вы не сможете написать программу.
Наводящие вопросы:

Цитата: WantToProg

к серверу приходят сообщения типа:
46064226
2000131467848
20 589


1) Какой они максимальной длины?
2) Если это текстовый протокол, то какая используется кодировка (ANSI, UTF-8, и т.д.)?
3) Сколько сообщений отправляет клиент?
4) Что нужно отвечать (если нужно) клиенту на каждое сообщение?

19K
24 ноября 2009 года
WantToProg
63 / / 19.01.2009
Цитата:
Когда вы наконец поймете (и расскажете тут), какой же длины сообщения:


Сообщения приходят посимвольно от устройства:
2000131467848 - это приходящие последовательно символы, т.е. 13 байт (точно измерить не могу сейчас)
Все сообщения разной длины, но чтоб удостоверится, отпишусь завтра, надо глянуть будет.
Клиентом является устройство, которое может быть TCP клиентом. На прикладном уровне я не скажу.
Клиент отправляет одно сообщение, с набором этих символов.
Я тут подумал, что можно сделать так

Код:
using (TcpClient c = listener.AcceptTcpClient())
                using (NetworkStream n = c.GetStream())
                {
                    MessageBox.Show("connected");

                    char[] msg = new BinaryReader(n).ReadChars(256);

                    string chartomsg = new string(msg);

                    for (i = 0; i < data.Count(); i++)
                        if (data == chartomsg)
                        {
                            int k = i + 2;
                            strmsg = data[k] + data[k + 1];
                            BinaryWriter w = new BinaryWriter(n);
                            char[] msgtochar = strmsg.ToCharArray();
                            w.Write(msgtochar);
                            w.Flush();
                        }
                }

            }
        listener.Stop();


Я постараюсь упростить объяснение кодом. Очень признателен вам, за отклик.
В общем, я приложу файл, в котором написан данный сервер для этого устройства на C, полностью рабочий. А вот как реализовать его в C#?.... Не думаю, что слишком отличается от Windows кода, разве что библиотеками.
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог