while()消耗大量CPU资源

ServerSocket监听,这种使用是为了保证它中的程序一直运行着   能够在任何时候获得内容并执行(传递。。。。。) 许多应用,都是使用死循环的,因为我们在里面可以
1 sleep 休息
2 return / break 退出循环
举例:在通讯中如果不使用就成为了点对点的通讯了(SOCKET   通讯中)

如果要实现while(true)只要给他再重开一个线程就行了,这个一般应用于做通信方面,由于在接收时会发生堵塞,所以接收方面需要重开一个线程,线程里就是while(true){不停的等待发来的消息}

在Socket编程中,要采用多线程去处理网络流,客户端需要不停的去监听端口中是否有数据过来,这里采用基本的流收发,DataInputStream在所有的read方法都是阻塞的,只有available这一个方法是非阻塞的,当我判断是否有流的时间,采用available但网络流无数据的时间造成了无限循环,使CPU的占用比达到50%,当去掉这个判断之后,当调用read方法的时间就阻塞到哪里,这样CPU的占用比为0%(约等于),可见我们在写程序的时间,要时刻关注我们程序里面的死循环,最好是在if后面加上else输出一句话,或者DEBUG一下。我倾向于前者,更加直观

死循环是可以的,控制权不是由程序控制的,即使你的程序是死循环,其他的应用程也是可以执行的,因为CPU的运行调度是系统来执行的,用线程最好使用sleep,用线程而不用sleep对CPU占有率影响特别大,所以考虑一个合适的sleep时间非常关键。需不需要sleep其实要看循环语句中的执行什么代码   如果有io的read()之类的会阻塞的代码  ,不sleep也可以的

   最近做一个java网络通讯的东西,在程序里原本有一段是这样的:
while(in.readLine()!=null){
      String aa=in.readLine();
}
       结果发现读取老是错误,后来我试了用下面的方法
while(true){
     String aa=in.readLine();
}
       结果读取成功!这程序咋一看差不多,我们考虑第一个程序,当程序读到,while(in.readLine()!=null)的时候,程序发生了阻塞,等待读入,如果读入成功,就执行下一个循环,下一个已开始也是阻塞,接着再读入,如此反复。而第二个是一开始就循环,但是读到String aa=in.readLine()的时候也发生阻塞,也是读入后才发生后面的事情,然后再循环,表明上看好像是一样的,但是结果为什么不一样呢!!!

       后来我才弄明白,原来第一个在读到while(in.readLine()!=null)的时候,如果有数据,那么执行String aa=in,readLine()的时候程序会继续往下读,也就是第一个while里面的读入被抛弃了,如果程序读入的只有是一行的话,那么这行就不会读入!!




 @Override
        public void run() {
            Log.d(TAG2, "Socket开始接收数据...");
            try {
                while (isReceive) {
                    if (socket != null && !socket.isClosed()) {
                        if (socket.isConnected() && !socket.isInputShutdown()) {//套接字的传入通道是否已关闭
                            if (inputStream.available() > 0) {
                                handle();
                            }
                            try {
                                Thread.currentThread().sleep(1);
                            } catch (InterruptedException e) {
                                e.printStackTrace();
                            }
                        }
                    }
                }
            } catch (IOException ex) {
                ex.printStackTrace();
                Log.d(TAG2, String.format("Error:接收数据时发生 %s 异常!", ex.getClass().getName()));
                if (ex instanceof java.net.SocketException) {
                    close();
                    initOriginalData();
                    sendBroadcast(new Intent(Constants.INTENT_ACTION.ACTION_NET_CONN_FAILURE));//通知连接中断
                } else if (ex instanceof java.net.SocketTimeoutException) {
                }
            }
        }


解决办法   sleep(1)