java基于NIO实现群聊模式

Java基于NIO实现群聊模式攻略

简介

Java NIO(New I/O)是Java 1.4版本引入的一组用于高效处理I/O操作的API。使用Java NIO,我们可以实现非阻塞的、事件驱动的I/O操作,这对于实现群聊模式非常有用。在本攻略中,我们将使用Java NIO来实现一个简单的群聊程序。

步骤

步骤1:创建服务器端

首先,我们需要创建一个服务器端来接收客户端的连接,并将接收到的消息广播给所有连接的客户端。

import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.*;
import java.util.Iterator;

public class Server {
    private Selector selector;
    private ServerSocketChannel serverSocketChannel;
    private ByteBuffer buffer = ByteBuffer.allocate(1024);

    public void start(int port) throws IOException {
        selector = Selector.open();
        serverSocketChannel = ServerSocketChannel.open();
        serverSocketChannel.configureBlocking(false);
        serverSocketChannel.bind(new InetSocketAddress(port));
        serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT);

        System.out.println(\"Server started on port \" + port);

        while (true) {
            selector.select();
            Iterator<SelectionKey> iterator = selector.selectedKeys().iterator();
            while (iterator.hasNext()) {
                SelectionKey key = iterator.next();
                iterator.remove();

                if (key.isAcceptable()) {
                    acceptConnection(key);
                } else if (key.isReadable()) {
                    broadcastMessage(key);
                }
            }
        }
    }

    private void acceptConnection(SelectionKey key) throws IOException {
        ServerSocketChannel serverChannel = (ServerSocketChannel) key.channel();
        SocketChannel clientChannel = serverChannel.accept();
        clientChannel.configureBlocking(false);
        clientChannel.register(selector, SelectionKey.OP_READ);
        System.out.println(\"New client connected: \" + clientChannel.getRemoteAddress());
    }

    private void broadcastMessage(SelectionKey key) throws IOException {
        SocketChannel clientChannel = (SocketChannel) key.channel();
        buffer.clear();
        int bytesRead = clientChannel.read(buffer);
        if (bytesRead == -1) {
            clientChannel.close();
            return;
        }
        buffer.flip();
        byte[] bytes = new byte[buffer.remaining()];
        buffer.get(bytes);
        String message = new String(bytes);
        System.out.println(\"Received message: \" + message);

        for (SelectionKey selectionKey : selector.keys()) {
            Channel channel = selectionKey.channel();
            if (channel instanceof SocketChannel && channel != clientChannel) {
                SocketChannel destChannel = (SocketChannel) channel;
                destChannel.write(ByteBuffer.wrap(bytes));
            }
        }
    }

    public static void main(String[] args) throws IOException {
        Server server = new Server();
        server.start(8080);
    }
}

步骤2:创建客户端

接下来,我们需要创建一个客户端来连接服务器,并发送和接收消息。

import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.SocketChannel;
import java.util.Scanner;

public class Client {
    private SocketChannel socketChannel;
    private ByteBuffer buffer = ByteBuffer.allocate(1024);

    public void start(String serverHost, int serverPort) throws IOException {
        socketChannel = SocketChannel.open();
        socketChannel.configureBlocking(false);
        socketChannel.connect(new InetSocketAddress(serverHost, serverPort));

        while (!socketChannel.finishConnect()) {
            // 等待连接完成
        }

        System.out.println(\"Connected to server: \" + socketChannel.getRemoteAddress());

        new Thread(() -> {
            try {
                while (true) {
                    buffer.clear();
                    int bytesRead = socketChannel.read(buffer);
                    if (bytesRead == -1) {
                        socketChannel.close();
                        return;
                    }
                    buffer.flip();
                    byte[] bytes = new byte[buffer.remaining()];
                    buffer.get(bytes);
                    String message = new String(bytes);
                    System.out.println(\"Received message: \" + message);
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }).start();

        Scanner scanner = new Scanner(System.in);
        while (true) {
            String message = scanner.nextLine();
            if (message.equalsIgnoreCase(\"exit\")) {
                socketChannel.close();
                break;
            }
            buffer.clear();
            buffer.put(message.getBytes());
            buffer.flip();
            socketChannel.write(buffer);
        }
    }

    public static void main(String[] args) throws IOException {
        Client client = new Client();
        client.start(\"localhost\", 8080);
    }
}

示例说明

示例1:运行服务器端

Server server = new Server();
server.start(8080);

示例2:运行客户端

Client client = new Client();
client.start(\"localhost\", 8080);

在示例2中,客户端将连接到本地主机的8080端口,并可以发送和接收消息。在服务器端示例1中,服务器将监听8080端口,并将接收到的消息广播给所有连接的客户端。

请注意,示例中的代码仅为演示目的,可能需要根据实际需求进行修改和扩展。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:java基于NIO实现群聊模式 - Python技术站

(0)
上一篇 2023年7月29日
下一篇 2023年7月29日

相关文章

  • maven学习笔记——maven环境配置(1)

    Maven学习笔记——Maven环境配置(1) 什么是Maven Maven是一款基于Java的项目管理和构建工具,可以帮助开发者更加轻松、高效地管理项目依赖、构建项目以及开发项目文档等任务,因此受到了广泛的应用。 安装Maven Maven的安装过程相对简单,在此不加赘述。可以通过以下步骤来安装: 在官网(https://maven.apache.org/…

    其他 2023年3月28日
    00
  • 深入Vue-Router路由嵌套理解

    深入Vue-Router路由嵌套理解攻略 Vue-Router是Vue.js官方的路由管理器,它允许我们在Vue应用中实现页面之间的导航和路由功能。其中一个强大的特性是路由嵌套,它允许我们在一个路由中嵌套另一个路由,从而创建复杂的页面结构和嵌套的组件关系。本攻略将详细讲解Vue-Router路由嵌套的概念和用法。 1. 路由嵌套的基本概念 路由嵌套是指在一个…

    other 2023年7月27日
    00
  • oracle中读写blob字段的问题解析

    Oracle中读写BLOB字段的问题解析 1. BLOB是什么? BLOB是Binary Large Object的缩写,它是Oracle数据库中一种数据类型,通常用于存储图像、音频、视频等二进制格式的数据。 2. 读取BLOB字段 2.1 使用PL/SQL 在PL/SQL中,读取BLOB字段通常需要通过创建BFILE来实现。BFILE是BLOB的一个子类型…

    other 2023年6月25日
    00
  • html标签的嵌套

    以下是“HTML标签的嵌套”的完整攻略: HTML标签的嵌套 在HTML中,标签可以嵌套在其他标签中。这意味着您可以在一个标内部包含另一个标。以下是如何嵌套HTML标签的步骤: 1. 嵌套标签 要嵌套标签,需将一个标签放置在一个标签内部即可。例如,以下是一个包含标题和段落的HTML代码: <h1>这是一个标题</h1<p>这是一…

    other 2023年5月7日
    00
  • 代码质量检测-sonar

    代码质量检测-sonar 在软件开发过程中,代码质量一直是开发人员和项目经理非常注重的问题。而代码质量检测则成为了一个必要的过程,以确保代码的可读性、可维护性、可靠性等方面的优化。 在众多的代码检测工具中,SonarQube(以下简称sonar)是其中的一款非常受欢迎的工具。该工具不仅支持多种编程语言,而且提供了丰富的检测规则,帮助开发人员根据不同项目的需求…

    其他 2023年3月28日
    00
  • oracle数据库之rownum和rowid用法

    以下是详细讲解“Oracle数据库之ROWNUM和ROWID用法的完整攻略,过程中至少包含两条示例说明”的标准Markdown格式文本: Oracle数据库之ROWNUM和ROWID用法 在Oracle数据库中,ROWNUM和ROWID是两个常用的关键字,用于查询和操作表中的数据。以下是ROWNUM和ROWID的详细介绍和用法。 ROWNUM ROWNUM是…

    other 2023年5月10日
    00
  • tomcat的server.xml中的context节配置

    Tomcat 的 server.xml 中的 context 节配置 在 Tomcat 中,server.xml 是主要的配置文件之一,用于配置 Tomcat 的全局设置。context 节用于配置 Web 应用程序的上下文路径、文档根目录、会话管理等信息。本文将介绍如何在 server.xml 中配置 context 节。 步骤 以下是在 server.x…

    other 2023年5月9日
    00
  • 乐播投屏怎么查看版本号?乐播投屏查看版本号方法

    乐播投屏是一款用于将手机、平板等设备上的内容投射到电视屏幕上的应用程序。要查看乐播投屏的版本号,可以按照以下步骤进行操作: 打开乐播投屏应用:在您的设备上找到乐播投屏应用的图标,并点击打开。 进入设置界面:在乐播投屏应用的主界面上,通常会有一个设置图标,一般是一个齿轮或者三个竖直排列的点。点击该图标,进入设置界面。 查看版本号:在设置界面中,您可以找到一个关…

    other 2023年8月3日
    00
合作推广
合作推广
分享本页
返回顶部