我试图创建一个服务器,使用多个端口,因此不同的数据和信息可以很容易地发送和接收,但在我的doInBackground方法中,我的代码卡在一个socket.receive, 这里是我的代码doInBackground卡住
while(run)
{
//GameServerID
try
{
if(gameServerID == null)
{
gameServerID = new DatagramSocket(portID);
}
//try to receive data
byte[] buf = new byte[256];
DatagramPacket packet = new DatagramPacket(buf, buf.length);
try
{
Log.d(TAG, "Wait for something to connect");
gameServerID.receive(packet); <--GETS STUCK HERE
}
catch (IOException e)
{
Log.d(TAG, "Error with receiving data");
e.printStackTrace();
}
String data = new String(buf, 0, packet.getLength());
Log.d(TAG, data);
//Send out the ID to the client
byte[] bufer = new byte[256];
//Send a message "connect" to the host
String msg = Integer.toString(players);
players = players + 1;
bufer = msg.getBytes();
InetAddress address;
//Default ip address of the host
address = packet.getAddress();
DatagramPacket p = new DatagramPacket(bufer, bufer.length , address, portID);
//Send packet
gameServerID.send(p);
addresses.add(address);
}
catch (SocketException e)
{
Log.d(TAG, "Error with socket");
e.printStackTrace();
}
//Listen for a client to connect
catch (IOException e)
{
Log.d(TAG, "Error with I/O");
e.printStackTrace();
}
//GameServerPositions
try
{
Log.d(TAG, "Run the gamePositions code");
if(gamePositions == null)
{
gamePositions = new DatagramSocket(portPos);
}
//Receive position
//try to receive data
byte[] buf = new byte[256];
DatagramPacket packet = new DatagramPacket(buf, buf.length);
try
{
gamePositions.receive(packet);
}
catch (IOException e)
{
Log.d(TAG, "Error with receiving data");
e.printStackTrace();
}
String data = new String(buf, 0, packet.getLength());
Log.d(TAG, data);
String[] pos = data.split(":");
for(int i = 0;i<pos.length;i++)
{
Log.d(TAG, pos[i]);
}
xValues[ Integer.parseInt(pos[0]) ] = Integer.parseInt(pos[1]);
yValues[ Integer.parseInt(pos[0]) ] = Integer.parseInt(pos[2]);
}
catch (SocketException e)
{
Log.d(TAG, "Error with socket");
e.printStackTrace();
}
//Listen for a client to connect
catch (IOException e)
{
Log.d(TAG, "Error with I/O");
e.printStackTrace();
}
//GameServerSendPos
try
{
Log.d(TAG, "Run the gamePositionsSend code");
String data = "";
if(gameSendPos == null)
{
gameSendPos = new DatagramSocket(portSend);
}
//create the string ready to be sent out
for(int i = 0; i < 8; i++)
{
if(xValues[i] >= 0)
{
data += i + ":" + xValues[i] + ":" + yValues[i] + ":";
}
}
byte[] bufer = new byte[256];
bufer = data.getBytes();
DatagramPacket p = null;
for(int i = 0;i < addresses.size(); i++)
{
if(addresses.get(i) != null)
{
p = new DatagramPacket(bufer, bufer.length , addresses.get(i), portSend);
gameSendPos.send(p);
}
}
}
catch (SocketException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
catch (IOException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
}
我该怎么办才能阻止它卡住,或经过这么长时间的等待后,才跳过它?只是更多的信息,当第一个客户端连接,代码工作正常,直到它再次到达顶部,然后socket.received只是卡纸起来......
帆布
更新
我有我的代码更改为3个不同的班,我开始他们在我的服务器,同时循环,像这样
while(run)
{
if(start == true)
{
gsID.doInBackground();
addresses = gsID.addresses;
gsPos.addresses = addresses;
gsPos.doInBackground();
gsSendPos.addresses = addresses;
gsSendPos.positions = gsPos.positions;
gsSendPos.doInBackground();
start = false;
}
else
{
addresses = gsID.addresses;
gsPos.addresses = addresses;
gsSendPos.addresses = addresses;
gsSendPos.positions = gsPos.positions;
}
}
但它仍然再次被卡住的gameServerID接收方法。
我只是改变了所有的类到线程,它的效果更好,但在Android 4.0 +线程的更高版本不能从UI使用,但我不知道我是如何开始他们从不是UI?
是的,正如我在答复中提到,它被“卡住”,因为'receive()'是一个阻塞的IO调用,它坐等数据可用于输入流。这段代码在你的服务器中,所以线程应该没问题。在UI方面,如果需要的话,您可以从UI线程向服务器发送数据(不熟悉Android开发)。如果你想避免在服务器上线程化并使用非阻塞IO,也检查我在NIO上的链接。换句话说, – Avi 2013-04-05 00:24:06