один сервер несколько клиентов - PullRequest
2 голосов
/ 01 февраля 2011

Я сталкиваюсь со следующими проблемами:

  1. Мне нужно написать серверную программу, которая будет принимать несколько клиентов
  2. все клиенты подписываются на одни и те же данные с сервера, например,обновление цены акций.
  3. каждый клиент может отправлять на сервер простые команды, такие как «вход в систему», «остановка»

Так вот мое решение, так как я не очень опытен в многопоточностиTCP, я хочу знать, это хорошее решение?если нет, есть ли лучшее решение?Нужно ли иметь поток для каждого клиентского сокета?Спасибо BTW: извините за смущение каждого, это небольшой проект, который включает в себя только 5-10 классов.

class AcceptThread {
    ......
    public void run () {
        ControlThread controlThread = new ControlThread();
        controlThread.start();

        Socket socket = new Socket(port);
        while (!stop) {
            Socket s = socket.accept();
            controlThread.addClient (s);
        }
    }
}

class ControlThread {
    Set<Scoket> clients;
    SendDataThread sendDataThread;  

    public ControlThread () {
        sendDataThread = new SendDataThread();
        sendDataThread.start();     
    }

    public void addClient (Socket socket) {
        clients.add(socket);
        sendDataThread.addListener(socket);
    }

    public void run () {
        ......
        for (Socket s : clients) {
            if (s.getInputStream().available()) {
                //read command from s
            }
        }
        ......              
    }
}

class SendDataThread () {
    Set<Scoket> listeners;

    public void addListener (Socket s) {
        listeners.add(s);
    }

    public void run () {
        for (Socket s: listeners) {
            // send data to each listener
        }
    }
}

Ответы [ 4 ]

3 голосов
/ 01 февраля 2011

необходимо ли иметь поток для каждого клиентского сокета?

Нет, на самом деле, я бы даже не рекомендовал его.Если это небольшой проект и вы не хотите использовать какую-либо существующую библиотеку, я бы посоветовал вам использовать пакет java.nio и SelectableChannels.С помощью так называемого селектора вы можете легко отслеживать входящие данные клиентов неблокирующим способом.

Вот несколько полезных ссылок:

0 голосов
/ 01 февраля 2011

Другие упоминали, что вы можете использовать библиотеку nio, чтобы уменьшить количество необходимых потоков.я просто хотел указать, что ваш текущий пример кода не будет работать.Вы должны использовать поток на сокет при использовании стандартных потоков IO.available() метод практически бесполезен (в общем) и не остановит ваш поток управления от блокировки.

0 голосов
/ 01 февраля 2011

Спасибо BTW: извините за путаницу, это небольшой проект, в котором участвуют только 5-10 классов.

В этом нет ничего плохого.Все абстракции более высокого уровня так или иначе основаны на сокетах.Если ваш проект не достаточно большой, нет необходимости использовать ряд других фреймворков / инструментария для выполнения той же работы.Потоки дешевы (и могут даже извлечь выгоду из многоядерной архитектуры), хотя использование SelectableChannels, как предложил @aioobe, тоже неплохая идея.

Когда ваши проекты требуют этого, вы всегда можете узнать о других методах межпроцессного взаимодействия (передача сообщений, удаленный вызов метода и т. Д., А также о его 100 реализациях).

Однако вы можете захотеть ограничить количество потоков, которые сервер использует одновременно.Это может быть легко достигнуто путем запроса, например, семафора размером, равным количеству потоков, которые вы хотите обслуживать.Еще одна интересная вещь, которую стоит рассмотреть, - это использование java пулов потоков для более эффективного повторного использования ваших ресурсов.

0 голосов
/ 01 февраля 2011

Как насчет использования стандартных технологий для решения этой проблемы?

JMS тема Механизм распространения для публикации доставленных сообщений нескольким подписчикам.

Учебник

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