2

学習課題として書いた Java アプリケーションを scala に移植しています。その一部は、TCP を介して直接プロトコルを使用して別のマシンと通信しています。このプロトコルには、対応するヘッダーとトレーラーを持つ 2 つのレイヤー (アプリケーションとトランスポート) があります。したがって、特定のメッセージは次のようになります

ヘッダー | aヘッダー | メッセージ | 予告編 | tトレーラー

私は

trait Layer{
   def write(s:String) : Unit
   def read :String
}

各レイヤーは、ヘッダー|トレーラーでメッセージを完成させ、次のレイヤーに渡します。次に、次のような実装で組み合わせることができるaTransportLayerと aがありますApplicationLayer

 val layer = new TcpLayer with ApplicationLayer with TransportLayer

コンポーネントを自由に再利用できるこのデザインには感激しました。そして、私のジレンマが現れました:

  • 副作用を避けるために、writeメソッドは を返すUnitのではなく、変更されStringた を送信する必要があります。これにより、副作用が最小限に抑えられ、テストが容易になりますが、クライアント コードはStringソケット自体を介して完了したものを送信する必要があります (これには既に副作用がありますが、それを回避する方法はありませんか?)。
  • クライアントコードは「起動して忘れる」必要があるためwrite、指定されたものを呼び出すことができLayer、変更されたものを気にする必要はありませんString(とにかく彼には意味不明かもしれません)。Unitしたがって、戻り値は return が正しい選択だと思います。

どのバージョンがより関数型プログラミングに適しているかについての思慮深い洞察はありますか?

4

1 に答える 1

1

唯一の副作用がソケットにある場合は、次のようにします。

val layers = new TcpLayer with ApplicationLayer with TransportLayer
socket.write (layers.write (message))
unitTestEngine.check (layers.write (message))

または、クライアントがlayer作業する必要がある場合は、次のようになります。

val layers = new TcpLayer (socket) with ApplicationLayer with TransportLayer
layers.sink (layers.write (message))
unitTestEngine.check (layers.write (message))

sinkSocket インスタンスを返すメソッドはどこにありますか。

于 2013-04-19T18:19:56.770 に答える