我有两个Android设备,一个充当客户端,另一个充当服务器。我试图从服务器设备获取n
个数量的图像。以前,为了获取一个图像,我使用AsyncTask
在客户端设备上创建并打开Socket
连接。并且一个线程在ServerSocket
的服务器设备上运行。两者都配置为使用相同的端口。
我想查询一些图片。由于连接在同一个端口,我不认为我可以同时发送这些查询?这可能吗?
我正在考虑创建一个Queue
AsyncTask
并逐个执行它们。但在阅读了一些有关此问题的帖子后,AsyncTask
似乎不是正确的方法,而且AsyncTask线程的数量有限制。
Android开发者网站建议IntentService
对执行此类任务很有用。所以我写了一个基础课。
public class ClientSyncService extends IntentService {
private JSONObject jsonData;
private static final int SocketServerPORT = 4000;
private String hostAddress;
private Bitmap queryBitmap;
private static final String TAG = "ClientSyncService";
private String requestString;
public ClientSyncService(String name) {
super(name);
}
@Override
protected void onHandleIntent(Intent workIntent) {
String jsonString = workIntent.getDataString();
hostAddress = workIntent.getStringExtra("host-ipaddress");
try {
jsonData = new JSONObject(jsonString);
} catch (JSONException e) {
e.printStackTrace();
}
try {
requestString = jsonData.getString("request");
} catch (JSONException e1) {
e1.printStackTrace();
}
Socket socket = null;
DataInputStream dataInputStream = null;
DataOutputStream dataOutputStream = null;
try {
socket = new Socket(hostAddress, SocketServerPORT);
dataOutputStream = new DataOutputStream(
socket.getOutputStream());
dataInputStream = new DataInputStream(socket.getInputStream());
dataOutputStream.writeUTF(jsonData.toString());
Log.i(TAG, "waiting for response from host");
if (requestString == null) {
socket.close();
return;
}
if (requestString == "query-display-picture" || requestString == "query-album-art") {
Log.i(TAG, "waiting for image");
byte buf[] = new byte[4096];
ByteArrayOutputStream bos = new ByteArrayOutputStream();
int len;
while((len = dataInputStream.read(buf)) != -1) {
bos.write(buf, 0, len);
bos.flush();
}
if (bos.size() > 0) {
queryBitmap = BitmapFactory.decodeByteArray(bos.toByteArray(), 0, bos.size());
} else {
Log.i(TAG, "bitmap is null");
}
Log.i(TAG, "bitmap created");
}
} catch (IOException e) {
e.printStackTrace();
} finally {
// close socket and streams
}
}
我将详细说明有关将数据广播到活动的其余部分。我不清楚如何调用此IntentService
。我是否为每个图像查询准备一个队列并创建新的意图服务,或者将所有图像请求传递给意向服务,该服务将有一个循环并向服务器发送请求并获取数据。
TL; DR :我想从客户端获取n个图像/文件(最好使用相同的端口)。最好的方法是什么?我已阅读有关ThreadPoolExecutor
和BlockingQueue
的内容,但尚未尝试使用它们。我对线程有点新意。
答案 0 :(得分:0)
您可以将多个套接字从客户端连接到同一个主机:端口,这只会在服务器上创建更多套接字,您需要多个线程接受服务器上的连接。
或者可以使用要获取的图像列表创建单个AsyncTask,并将它们一个接一个地获取。您还可以对多个图像进行单个请求,并将它们全部放在同一个套接字中(例如,通过发送大小/数据/大小/数据/ ...或者使用某些内容作为Google协议缓冲区(重复字段就可以了) 。
最后一个选项可能是让工作线程在队列中获取请求(每个映像一个请求)并逐个处理它们。
答案 1 :(得分:0)
我认为最好的方法是仅按顺序获取这些图像。 但我认为普通的java线程是最好的。
理想情况下,AsyncTasks应该用于短时间操作(几秒钟) 最多。)如果你需要保持线程长时间运行 时间,强烈建议您使用提供的各种API java.util.concurrent pacakge,如Executor,ThreadPoolExecutor 和FutureTask。