Java Android中的StreamCorruptedException

Java Android中的StreamCorruptedException,java,android,Java,Android,所以我必须用Android客户端实现一个推荐系统。系统的工作原理如下:用户将其位置和所需建议的数量发送到服务器。然后,服务器生成建议并发回建议的POI(兴趣点) 这是我的问题。当客户端从服务器读取Pois[]数组(实际建议)时,将抛出StreamCorruptedException。奇怪的是,当我在自己的电脑上运行应用程序时,这种情况从未发生过。只有当我在大学的计算机上运行它时才会发生。但这并不总是发生。它可能发生8/10次,我运行它 任何帮助都将不胜感激。这是个例外 java.io.Strea

所以我必须用Android客户端实现一个推荐系统。系统的工作原理如下:用户将其位置和所需建议的数量发送到服务器。然后,服务器生成建议并发回建议的POI(兴趣点)

这是我的问题。当客户端从服务器读取
Pois[]
数组(实际建议)时,将抛出
StreamCorruptedException
。奇怪的是,当我在自己的电脑上运行应用程序时,这种情况从未发生过。只有当我在大学的计算机上运行它时才会发生。但这并不总是发生。它可能发生8/10次,我运行它

任何帮助都将不胜感激。这是个例外

java.io.StreamCorruptedException: invalid type code: 3A
    at java.io.ObjectInputStream.readClassDesc(ObjectInputStream.java.1521)
    at java.io.ObjectInputStream.readOrdinaryObject(ObjectInputStream.java:1772)
    at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1351)
    at java.io.ObjectInputStream.defaultReadFields(ObjectInputStream.java:1992)
    at java.io.ObjectInputStream.readSerialData(ObjectInputStream.java:1916)
    at java.io.ObjectInputStream.readOrdinaryObject(ObjectInputStream(1799)
    at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1351)
    at java.io.ObjectInputStream.readArray(ObjectInputStream.java:1707)
    at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1345)
    at java.io.ObjectInputStream.readUnshared(ObjectInputStream.java:463)
    at client.ds2018.ClientActivity$Fetcher.fetch(ClientActivity.java:283)
    at client.ds2018.ClientActivity$Fetcher.doInBackground(ClientActivity.java:311)
    at client.ds2018.ClientActivity$Fetcher.doInBackground(ClientActivity.java:256)
    at android.os.AsyncTask$2.call(AsyncTask.java:305)
    at java.util.concurrent.FutureTask.run(FutureTask.java:237)
    at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:243)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java.1133)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
    at java.lang.Thread.run(Thread.java:761)
这是代码。 这是
Poi
类。其中的一个数组作为响应发送给客户端

public class Poi implements Serializable
{
    private int id; // Poi id
    private byte[] image; // Binary representation of location's image.
    private double latitude, longitude;
    private String name, category, imageURL; // The url address of the image.

    // Constructor, getters & setters[...]
}
public class ClientActivity extends AppCompatActivity implements OnMapReadyCallback
{
    private Fetcher f; // The async task that fetches the Pois.
    private Poi[] recs; // Recommendations array.
    private int uid, k; // User id and number of recommendations.

    private class Fetcher extends AsyncTask<Void, Void, Poi[]>
    {
        Poi poi;
        int k, uid;
        ProgressDialog dialog;
        Socket request = null;
        ObjectInputStream in = null;
        ObjectOutputStream out = null;

        Fetcher(Poi poi, int k, int uid)
        {
            this.k = k;
            this.uid = uid;
            this.poi = poi;
        }

        @Override 
        protected Poi[] doInBackground(Void... v)
        {
            Poi[] result = null;

            try
            {
                request = new Socket(IP_ADDRESS, PORT);
                out = new ObjectOutputStream(request.getOutputStream());
                in = new ObjectInputStream(request.getInputStream());

                result = fetch(); // <-- Gets null.
            }
            catch(IOException ioExc)
            {
                ioExc.printStackTrace();
            }
            finally
            {
                try
                {
                    out.close();
                    in.close();
                    request.close();
                }
                catch(IOException ioExc)
                {
                    ioExc.printStackTrace();
                }
            }

            return result;
        }

        Poi[] fetch() throws IOException
        {
            Poi[] recs = null;

            try
            {
                out.writeInt(uid);
                out.writeUnshared(LOCATION);
                out.writeInt(k);
                out.flush();

                recs = (Poi[]) in.readUnshared(); // <-- This is where the exception is thrown, readUnshared returns null.
            }
            catch(ClassNotFoundException cnfExc)
            {
                cnfExc.printStackTrace();
            }

            return recs; // <-- Returns null.
        }

    private static final Poi LOCATION = // The location sent to the Server...;
}
public class Master
{
   private JSONObject pois;

   //  Constructor.
   public Master() { initialize(); }

   private void openServer()
   {
        // Do stuff[...]
        try
        {
            Thread t;
            //  Awaiting clients.
            System.out.println("Awaiting clients...\n");
            provider = new ServerSocket(C_PORT, BACKLOG);

            while(true)
            {
                connection = provider.accept();
                System.out.println("Client connected.");

                //  Creating request handler.
                t = new Handler(connection);

                t.start();
            }
           catch{Exception exc) {...}
           finally
           {
               try
               {
                   //  Closing server.
                   provider.close();
               }
               catch(IOException ioExc)
               {
                   ioExc.printStackTrace();
               }
           }
       }


       //  Returns the recommendations.
       private synchronized Poi[] getRecommendations(int u, int k, Poi poi)
       {
           // Produce recommendations...
       }

       // The Handler class handles the client requests.
       private class Handler extends Thread
       {
           private Poi poi;    //  POI received by the client.
           /*
            *  k: multitude of POIs to recommend.
            *  u: user id.
            */
            private int k, u;
            private Poi[] recs;     // Recommendations for the client.
            private Socket connection;

            public Handler(Socket connection) { this.connection = connection; }

            //  Extending Thread class.
            public void run()
            {
                ObjectInputStream in = null;
                ObjectOutputStream out = null;

               try
               {
                   //  Initializing streams.
                   in = new ObjectInputStream(connection.getInputStream());
                   out = new ObjectOutputStream(connection.getOutputStream());

                   u = in.readInt();       //  User id.
                   poi = (Poi) in.readUnshared();    //  POI.
                   k = in.readInt();       //  Number of POIs.

                   //  Producing recommendations.
                   recs = getRecommendations(u, k, poi);

                   //  Sending recommendations to client.
                   out.writeUnshared(recs); // <-- This does NOT send null.
                   out.flush();
              }
              catch(EOFException oefExc)
              {
                   System.out.println("Client disconnected.\n");
              }
              catch(IOException ioExc)
              {
                   ioExc.printStackTrace();
              }
              catch(ClassNotFoundException cnfExc)
              {
                   cnfExc.printStackTrace();
              }
              finally
              {
                   try
                   {
                        //  Closing streams and socket.
                        in.close();
                        out.close();
                        connection.close();
                   }
                   catch(IOException ioExc)
                   {
                        ioExc.printStackTrace();
              }
          }
      }
这是
ClientActivity
类(客户端)


所以我想出来了。我没有让服务器下载图像,然后将它们与所有其他数据一起发送到客户端,而是让客户端自己下载图像。我想我可以发送的数据量有某种限制。

我不会使用Java ObjectStream进行数据传输,因为它可能会在你的应用程序中造成安全漏洞。使用不同的数据传输协议标准,如JSON、protobuf、…@Robert即可。谢谢你的提示。