Memorandums?

This blog is written about technical-discoveries and daily-events.

Socket通信アプリケーション備忘録 No.2

前回からの改善点

前回のエントリーはコチラ。meriyasu-blog.hatenablog.com

まずは、単純なミス。
サーバー側でクライアントに対応するための各スレッドにSocketインスタンスを渡すのを
忘れていました。
これでは、スレッド生成しても、クライアントの判別ができないので意味がありません。

MyThreadManager thread = new MyThreadManager(socket);
thread.start();

もちろん、MyThreadManagerは、Threadをextendsします。
このほかにも、startメソッドオーバーロードし、Socketを受けるstartメソッドを作るという手もあります。


次に通信について。
これまでの考え方では、

ローカルにおいて、座標情報などはすべてリスト(ArrayList, HashMap)に保存し、
リストをリモート側に送信する。
適宜、ファイル化する。
送信・受信形態は、Object Output/Input Streamクラスを利用し、
#writeObject, #readObjectを使用する。

しかし、重大な欠陥が判明...
ObjectOutputStream/ObjectInputStreamは、
通信するデータは直列化されていなければ、ならない。
つまり、シリアライズなどをしなくてはいけません。
ArrayListには、独自クラスのインスタンスなどを格納しており、
その独自クラスも、Serializableインターフェースを実装し、シリアライズUIDも設定していたのですが、
なぜか、うまく動作しません。
デバッグによりわかったことは、

ObjectInputStreamのインスタンス生成時にフリーズしている。

ということです。
つまり、送信するデータなど関係なかったのです。
StackOverFlowなどにもこのようなエラーについて、
OutputStreamを先に定義しろ、
などの記述がありましたが、それは関係ありませんでした。(もしわかる方がおられれば教えてください)

結局、違う通信形態をとることに。
その方法について、入力側は、BufferredInputStreamを用い、
出力側は、PrintWriterを用います。
また、BufferredInputStreamは任意のオブジェクトを扱えるわけではないので、
データは文字列型にしました。
文字列型を受け取ったのち、ローカル上解析メソッドで、要素をリスト形式で返す仕組みにしました。

いろいろ試行錯誤した結果、、、
なんとか完成しました。

あとは、オプション機能を付け加えていくだけです...