Подтвердить что ты не робот

Понимание ввода-вывода Ise при чтении сокета в Ruby

У меня есть код, который я использую для получения данных из сетевого сокета. Он отлично работает, но я пробил себе путь через пробную версию и ошибку. Я смиренно признаю, что я не совсем понимаю, как это работает, но я бы очень хотел. (Это был рабочий код, обработанный грузом, который я нашел)

Часть, которую я не понимаю, начинается с "ready = IO.select..." Я не понимаю:

  • Что делает IO.select(я попытался посмотреть его, но еще больше запутался с Kernel и что-нет)
  • что аргумент массива для IO.select для
  • что готово [0] делает
  • общая идея чтения 1024 байта? в то время

Здесь код:

@mysocket = TCPSocket.new('192.168.1.1', 9761)

th = Thread.new do
    while true
        ready = IO.select([@mysocket])
        readable = ready[0]

        readable.each do |socket|
            if socket == @mysocket
                buf = @mysocket.recv_nonblock(1024)
                if buf.length == 0
                    puts "The server connection is dead. Exiting."
                    exit
                else
                    puts "Received a message"
                end
            end
        end

    end
end

Спасибо, что помог мне "научиться ловить рыбу". Мне не нравятся биты моего кода, которые я не совсем понимаю - он просто работает по совпадению.

4b9b3361

Ответ 1

1) IO.select принимает набор сокетов и ждет, пока не будет возможно их прочитать или написать (или если произойдет ошибка). Он возвращает событие сокетов, которое произошло с.

2) массив содержит сокеты, проверенные для событий. В вашем случае вы указываете только сокеты для чтения.

3) IO.select возвращает массив массивов сокетов. Элемент 0 содержит сокеты, которые вы можете прочитать, элемент 1 - сокеты, которые вы можете записать, и элементы 2 - сокеты с ошибками.

После получения списка сокетов вы можете прочитать данные.

4) да, аргумент recv_nonblock - размер в байте. Обратите внимание, что размер фактически просматриваемых данных может быть меньше 1024, в этом случае вам может потребоваться повторить select (если фактические данные важны для вас).