多线程是这样一种机制,它允许在程序中并发执行多个指令流,每个指令流都称为一个线程,彼此间互相独立。线程又称为轻量级进程,它和进程一样拥有独立的执行控制,由 *** 作系统负责调度。
多线程是多任务的特殊形式。通常,有两种类型的多任务:基于进程和基于线程的多任务。进程本质上是正在执行的程序。因此,基于进程的多任务就是允许您的计算机同时运行两个或者更多程序的特性。例如,基于进程的多任务允许您在使用电子制表软件或者浏览Internet的同时运行文字处理程序。在基于进程的多任务中,程序是调度程序可以分派的最小代码单元。
多线程是为了使得多个线程并行的工作以完成多项任务,以提高系统的效率。线程是在同一时间需要完成多项任务的时候被实现的。
使用线程的好处有以下几点:
·使用线程可以把占据长时间的程序中的任务放到后台去处理
·用户界面可以更加吸引人,这样比如用户点击了一个按钮去触发某些事件的处理,可以d出一个进度条来显示处理的进度
·程序的运行速度可能加快
·在一些等待的任务实现上如用户输入、文件读写和网络收发数据等,线程就比较游泳了。在这种情况下我们可以释放一些珍贵的资源如内存占用等等。
还有其他很多使用多线程的好处,这里就不一一说明了。
多线程应用
我们以客户/服务器应用模式中如何进行服务器程序设计为例,来说明多线程技术的应用。该程序是在DECnet-VAX网络邮箱上实现的。对于TCP/IP,除了改用捆绑的套接字(socket)来代替DECnet中的网络邮箱以监视客户的服务请求外,其他方面基本上是一样的。
为了简化说明,假定该服务程序只提供2类功能,分别由函数funcl( )和func2( )来实现。客户在请求服务时要指明功能号1或2。另外限制需要同时提供服务的客户数目。
多线程程序的基本设计思想是,为请求服务的每个客户建立1个线程,专门为该客户提供服务。限制客户数目就是限制同时存在的线程数目。这些动态建立的线程对象存放在数组中。通过查找该数组是否有空槽,来决定是否达到最大数目。同时利用该数组来管理这些动态存在的线程及相应的网络链路。整个程序由1个主程序和提供2类服务的2个子程序组成。主程序(主控线程)在完成初始化 *** 作后,开始循环读取邮箱中的网络控制信息;在接收到连接请求信息后,主控线程就建立1个新线程,并指定相应的函数作为执行代码;如果客户要断开连接,则主控线程查找到相应的服务线程号,释放该服务线程使用的网络链路,并删除此线程。
这个问题有点搞笑!!!
用户多,不代表你服务器访问量大,访问量大不一定你服务器压力大!我们换成专业点的问题,高并发下怎么优化能避免服务器压力过大?
1,整个架构:可采用分布式架构,利用微服务架构拆分服务部署在不同的服务节点,避免单节点宕机引起的服务不可用!
2,数据库:采用主从复制,读写分离,甚至是分库分表,表数据根据查询方式的不同采用不同的索引比如btree,hash,关键字段加索引,sql避免复合函数,避免组合排序等,避免使用非索引字段作为条件分组,排序等!减少交互次数,一定不要用select!
3,加缓存:使用诸如memcache,redis,ehcache等缓存数据库定义表,结果表等等,数据库的中间数据放缓存,避免多次访问修改表数据!登录信息session等放缓存实现共享!诸如商品分类,省市区,年龄分类等不常改变的数据,放缓存,不要放数据库!
同时要避免缓存雪崩和穿透等问题的出现导致缓存崩溃!
4,增量统计:不要实时统计大量的数据,应该采用晚间定时任务统计,增量统计等方式提前进行统计,避免实时统计的内存,CPU压力!
5,加服务器:等大文件,一定要单独经过文件服务器,避免IO速度对动态数据的影响!保证系统不会因为文件而崩溃!
6,HTML文件,枚举,静态的方法返回值等静态化处理,放入缓存!
7,负载均衡:使用nginx等对访问量过大的服务采用负载均衡,实现服务集群,提高服务的最大并发数,防止压力过大导致单个服务的崩溃!
8,加入搜索引擎:对于sql中常出现的like,in等语句,使用lucence或者solr中间件,将必要的,依赖模糊搜索的字段和数据使用搜索引擎进行存储,提升搜索速度!#注意:全量数据和增量数据进行定时任务更新!
9,使用消息中间件:对服务之间的数据传输,使用诸如rabbitmq,kafka等等分布式消息队列异步传输,防止同步传输数据的阻塞和数据丢失!
10,抛弃tomcat:做web开发,接触最早的应用服务器就是tomcat了,但是tomcat的单个最大并发量只能不到1w!采取netty等actor模型的高性能应用服务器!
11,多线程:现在的服务器都是多核心处理模式,如果代码采用单线程,同步方式处理,极大的浪费了CPU使用效率和执行时间!
12,避免阻塞:避免bio,blockingqueue等常常引起长久阻塞的技术,而改为nio等异步处理机制!
13,CDN加速:如果访问量实在过大,可根据请求来源采用CDN分流技术,避免大流量完成系统崩溃!
14,避免低效代码:不要频繁创建对象,引用,少用同步锁,不要创建大量线程,不要多层for循环!
还有更多的细节优化技术,暂时想不起来了!
多有多个 CPU 可用。单核机器上多线程的优势不明显。线程间有共享数据。如果没有共享数据,用模型 3b 就行。虽然我们应该把线程间的共享数据降到最低,但不代表没有;
共享的数据是可以修改的,而不是静态的常量表。如果数据不能修改,那么可以在进程间用 shared memory,模式 3 就能胜任。
提供非均质的服务。即,事件的响应有优先级差异,我们可以用专门的线程来处理优先级高的事件。防止优先级反转。服务器连接超时就是在程序默认的等待时间内没有得到服务器的响应。
网络连接超时可能的原因有:
1、网络断开,不过经常显示无法连接。
2、网络阻塞,导致你不能在程序默认等待时间内得到回复数据包。
3、网络不稳定,网络无法完整传送服务器信息。
4、系统问题,系统资源过低,无法为程序提供足够的资源处理服务器信息。
5、设备不稳定,如网线松动、接口没插好等等。
6、网络注册时系统繁忙,无法回应。
7、网速过慢,如使用BT多线程下载,在线收看视频等大量占用带宽的软件,若使用共享带宽还要防范他人恶意占用带宽。
8、计算机感染了恶意软件,计算机病毒,计算机木马等。
扩展资料
解决方法:
1、请换个时间段再上或者换个目标网站。
2、检查双绞线是否合格。
3、用分区分段逐步排除的方法,排除回路故障。
4、DOS下用“Ping”命令对所涉及计算机逐一测试,网卡、集线器以及交换机是最容易出故障引起网速变慢的设备。
5、更换服务器网卡为100M或1000M、安装多个网卡、划分多个VLAN、改变路由器配置来增加带宽等。
6、必须及时升级所用杀毒软件;计算机也要及时升级、安装系统补丁程序,同时卸载不必要的服务、关闭不必要的端口,以提高系统的安全性和可靠性。
全文

远程服务-思科实力打造混合办公底层技术
根据服务器相关内容为您推荐远程服务
远程服务-思科高效协作工具重新定义混合办公。依托思科混合办公技术,助力企业打造有益于协作的安全基础设施。
思科系统中国网络技术有限公司广告
河南良悦科技-服务器故障服务器交换机维护一站式服务
值得一看的计算机服务器设备相关信息推荐
服务器故障各类服务器配件维护,机房维保。技术力量雄厚,服务响应快捷!资质认证,放心商家,良悦科技服务器故障专业技术咨询!
河南良悦信息科技有限公司广告
大家还在搜
汽车美容装饰加盟店
有没有什么相亲网站免费的
成人自考大专
手机传奇游戏
牛皮廨治疗
免费附近秒约
技能培训学校
升学教育
连接超时是什么意思
就是说你的本地PC跟另一个PC(大部分时候是SERVER)进行网络连接请求时,服务器没有多长时间没有给你回应,你的本地PC就会默认为连接超时,因为你的Pc一直处于等待服务器的回应,有回应就会进行下一步的流程。 超时,也就是time out。使用海外服务器呢,主要有以下几点区别。 一在国内访问的情况下,国内服务器快过国多线程技术可以提高cpu利用率,尤其是多核cpu的机器,提高并发执行效率。这是建立在cpu执行有空余的情况下的,多线程也并非没有代价,首先线程作为 *** 作系统的最小调度单位也是要占用内存空间的,其次线程调度及上下文切换也会消耗性能。一般线程数为cpu个数2+1较好,线程太多会占用内存,频繁的线程上下文切换也会导致效率降低。程序分Server和Client
服务器端打开侦听的端口,一有客户端连接就创建两个新的线程来负责这个连接
一个负责客户端发送的信息(ClientMsgCollectThread 类),
另一个负责通过该Socket发送数据(ServerMsgSendThread )
Serverjava代码如下:
/
创建日期 2009-3-7
TODO 要更改此生成的文件的模板,请转至
窗口 - 首选项 - Java - 代码样式 - 代码模板
/
package faueMutiUser;
import javaioBufferedReader;
import javaioIOException;
import javaioInputStreamReader;
import javaioPrintWriter;
import javanetServerSocket;
import javanetSocket;
/
服务器端
@author Faue
/
public class Server extends ServerSocket {
private static final int SERVER_PORT = 10000;
/
构造方法,用于实现连接的监听
@throws IOException
/
public Server() throws IOException {
super(SERVER_PORT);
try {
while (true) {
Socket socket = superaccept();
new Thread(new ClientMsgCollectThread(socket), "getAndShow"
+ socketgetPort())start();
new Thread(new ServerMsgSendThread(socket), "send"
+ socketgetPort())start();
}
} catch (IOException e) {
eprintStackTrace();
}
}
public static void main(String[] args) throws IOException {
new Server();
}
/
该类用于创建接收客户端发来的信息并显示的线程
@author Faue
@version 100
/
class ClientMsgCollectThread implements Runnable {
private Socket client;
private BufferedReader in;
private StringBuffer inputStringBuffer = new StringBuffer("Hello");
/
得到Socket的输入流
@param s
@throws IOException
/
public ClientMsgCollectThread(Socket s) throws IOException {
client = s;
in = new BufferedReader(new InputStreamReader(client
getInputStream(), "GBK"));
}
public void run() {
try {
while (!clientisClosed()) {
inputStringBufferdelete(0, inputStringBufferlength());
inputStringBufferappend(inreadLine());
Systemoutprintln(getMsg(inputStringBuffertoString()));
}
} catch (IOException e) {
//eprintStackTrace();
Systemoutprintln(clienttoString() + " is closed!");
}
}
/
构造显示的字符串
@param line
@return
/
private String getMsg(String line) {
return clienttoString() + " says:" + line;
}
}
/
该类用于创建发送数据的线程
@author Faue
@version 100
/
class ServerMsgSendThread implements Runnable {
private Socket client;
private PrintWriter out;
private BufferedReader keyboardInput;
private StringBuffer outputStringBuffer = new StringBuffer("Hello");
/
得到键盘的输入流
@param s
@throws IOException
/
public ServerMsgSendThread(Socket s) throws IOException {
client = s;
out = new PrintWriter(clientgetOutputStream(), true);
keyboardInput = new BufferedReader(new InputStreamReader(Systemin));
}
public void run() {
try {
while (!clientisClosed()) {
outputStringBufferdelete(0, outputStringBufferlength());
outputStringBufferappend(keyboardInputreadLine());
outprintln(outputStringBuffertoString());
}
} catch (IOException e) {
//eprintStackTrace();
Systemoutprintln(clienttoString() + " is closed!");
}
}
}
}
客户端:
实现基于IP地址的连接,连接后也创建两个线程来实现信息的发送和接收
/
创建日期 2009-3-7
/
package faueMutiUser;
import javaioBufferedReader;
import javaioIOException;
import javaioInputStreamReader;
import javaioPrintWriter;
import javanetSocket;
/
客户端
@author Faue
/
public class Client {
private Socket mySocket;
/
创建线程的构造方法
@param IP
@throws IOException
/
public Client(String IP) throws IOException {
try {
mySocket = new Socket(IP, 10000);
new Thread(new ServerMsgCollectThread(mySocket), "getAndShow"
+ mySocketgetPort())start();
new Thread(new ClientMsgSendThread(mySocket), "send"
+ mySocketgetPort())start();
} catch (IOException e) {
//eprintStackTrace();
Systemoutprintln("ServerIP:" + IP
+ " port:10000 can not be Connected");
}
}
public static void main(String[] args) throws IOException {
try {
new Client(args[0]);
} catch (Exception e) {
Systemoutprintln("输入的IP地址错误");
}
}
/
该类用于创建接收服务端发来的信息并显示的线程
@author Faue
@version 100
/
class ServerMsgCollectThread implements Runnable {
private Socket client;
private BufferedReader in;
private StringBuffer inputStringBuffer = new StringBuffer("Hello");
/
得到Socket的输入流
@param s
@throws IOException
/
public ServerMsgCollectThread(Socket s) throws IOException {
client = s;
in = new BufferedReader(new InputStreamReader(client
getInputStream(), "GBK"));
}
public void run() {
try {
while (!clientisClosed()) {
inputStringBufferdelete(0, inputStringBufferlength());
inputStringBufferappend(inreadLine());
Systemoutprintln(getMsg(inputStringBuffertoString()));
}
} catch (IOException e) {
//eprintStackTrace();
Systemoutprintln(clienttoString() + " is closed!");
Systemexit(0);
}
}
/
构造输入字符串
@param line
@return
/
private String getMsg(String line) {
return clienttoString() + " says:" + line;
}
}
/
该类用于创建发送数据的线程
@author Faue
@version 100
/
class ClientMsgSendThread implements Runnable {
private Socket client;
private PrintWriter out;
private BufferedReader keyboardInput;
private StringBuffer outputStringBuffer = new StringBuffer("Hello");
/
得到键盘的输入流
@param s
@throws IOException
/
public ClientMsgSendThread(Socket s) throws IOException {
client = s;
out = new PrintWriter(clientgetOutputStream(), true);
keyboardInput = new BufferedReader(new InputStreamReader(Systemin));
}
public void run() {
try {
while (!clientisClosed()) {
outputStringBufferdelete(0, outputStringBufferlength());
outputStringBufferappend(keyboardInputreadLine());
outprintln(outputStringBuffertoString());
}
outprintln("--- See you, bye! ---");
} catch (IOException e) {
//eprintStackTrace();
Systemoutprintln(clienttoString() + " is closed!");
Systemexit(0);
}
}
}
}
如果对您有帮助,请记得采纳为满意答案,谢谢!祝您生活愉快!
vaelac++实现多线程将文件从客户端发送到服务器端的具体步骤如下所示:
1、服务器端需要创建一个监听socket,并绑定一个本地IP地址和端口号,等待客户端连接到服务器。
2、客户端需要创建一个socket,并连接到服务器端的IP地址和端口号。
3、服务器端接收到客户端的连接请求后,创建一个新的线程,负责处理该客户端的文件传输请求。
4、在该线程中,服务器端需要接收客户端发送的文件名和文件大小等信息,并对其进行验证。
5、验证通过后,服务器端创建一个新的socket,用于与客户端建立文件传输连接。
6、在服务器端创建一个新的线程,负责接收客户端发送的文件数据,并将其写入服务器端的文件中。
7、在客户端中,创建一个新的线程,负责读取本地文件数据,并将其发送到服务器端。
8、客户端需要在发送文件之前,先发送文件名和文件大小等信息给服务器端,以便服务器端进行验证。
9、文件传输结束后,需要关闭所有的socket和线程。aspnet页面通常只能使用流行的浏览器支持的技术,扩展的客户端开发技术不在aspnet范围内。
假设你使用aspnet开发一个webService或者WCF服务,它的api可以这样设计(以WCF为例):
[ServiceContract]
public interface IFileService
{
[OperationContract]
void Upload(string fileName, long position, byte[] data);
}
这表示对文件fileName,从随机存取位置position开始写入data。客户端的应用程序(但是不是aspnet,因为aspnet只是一个服务器程序,客户端还是浏览器、脚本而不是aspnet在 *** 作的)可以读取本地文件,然后(例如)按照每10k字节作为一个块去顺序或者多线程调用服务,分块的好处在于如果通讯中断则可以断点续传。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)