首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >套接字与SocketChannel

套接字与SocketChannel
EN

Stack Overflow用户
提问于 2013-01-08 23:39:58
回答 3查看 47.3K关注 0票数 81

我正在努力理解SocketChannelsNIO。我知道如何使用常规套接字,以及如何制作一个简单的每个客户端线程服务器(使用常规阻塞套接字)。

所以我的问题是:

  • 什么是SocketChannel?
  • 在使用SocketChannel而不是套接字时,我得到了什么额外的好处。
  • 通道和缓冲区之间的关系是什么?
  • 什么是选择器?
  • 文档中的第一个sentance是A selectable channel for stream-oriented connecting sockets.。那是什么意思?

我读过同样的这份文件,但不知怎么的,我没有读到.

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2013-01-09 00:31:15

Socket是一种阻塞输入/输出设备。它使正在使用它的Thread在读取时阻塞,如果底层缓冲区已满,还可能会阻止写入。因此,如果服务器有一堆打开的Socket,则必须创建一组不同的线程。

SocketChannel是一种从套接字中读取数据的非阻塞方式,因此您可以让一个线程同时与一组打开的连接进行通信。这可以通过将一组SocketChannel添加到Selector中,然后在选择器的select()方法上循环,如果套接字已被接受、已接收数据或已关闭,该方法可以通知您。这允许您在一个线程中与多个客户端通信,而不需要多个线程和同步的开销。

Buffer是NIO的另一个特性,它允许您从读写中访问底层数据,以避免将数据复制到新数组中的开销。

票数 65
EN

Stack Overflow用户

发布于 2013-01-09 20:13:51

到目前为止,NIO已经太老了,很少有人记得1.4之前的NIO是什么样子的,为了理解NIO的“原因”,您需要知道这一点。

简而言之,到Java1.3为止,所有I/O都是阻塞类型的。更糟糕的是,没有select()系统调用多路I/O的模拟,因此,用Java实现的服务器别无选择,只能采用“每个连接一个线程”的服务策略。

在Java1.4中引入的NIO的基本要点是使传统的UNIX风格的多路复用非阻塞I/O功能在Java中可用。如果您了解如何使用select()poll()编程来检测一组文件描述符(通常是套接字)上的I/O准备状态,那么您将在NIO中找到所需的服务:对于非阻塞I/O端点使用SocketChannels,对于fdset或pollfd数组使用Selectors。现在,具有线程池或每个线程处理多个连接的服务器成为可能。这就是“额外的”。

Buffer是非阻塞套接字I/O所需的字节数组,特别是在输出/写入端。如果只能立即写入缓冲区的一部分,则使用阻塞I/O,您的线程就会被阻塞,直到整个线程都可以被写入为止。使用非阻塞I/O,您的线程将获得写入多少的返回值,让您来处理下一轮的剩余内容。Buffer通过显式实现生产者/使用者模式来处理这些机械细节,这样可以理解线程和JVM内核将不同步。

票数 21
EN

Stack Overflow用户

发布于 2014-06-03 09:14:01

即使您使用的是SocketChannels,也必须使用线程池来处理channels

考虑到场景,您只使用一个线程,它负责轮询select()和处理从Selectors中选择的SocketChannels,如果一个通道需要1秒来处理,并且队列中有10个通道,这意味着您必须在下一个轮询之前等待10秒,这是不可容忍的。因此,应该有一个用于通道处理的线程池。

从这个意义上说,我认为每个客户端的线程阻塞套接字模式并没有太大的不同。主要的区别在于NIO模式,任务较小,更像每个任务的线程,任务可以读、写、处理等等,更详细的是,您可以查看NettyNioServerSocketChannelFactory实现,它使用一个Boss线程接受连接,并将任务分派到一个工作线程池进行处理。

如果您真的喜欢一个线程,那么底线是至少您应该有一个集合的I/O线程,因为I/O操作通常比指令处理周期慢得多,所以您不希望一个宝贵的线程被I/O阻塞,而这正是NodeJS所做的,使用一个线程接受连接,并且所有的I/O都是异步的,并且由后端I/O线程池并行处理。

是旧的每一个客户端线程死了吗?我不这么认为,NIO编程很复杂,多线程也不是天生的邪恶,请记住,现代操作系统和CPU在多任务处理方面变得越来越好,因此多线程的开销随着时间的推移变得越来越小。

票数 6
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/14225957

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档