私はかなり単純なプロセッサ エミュレータを作成しようとしており、実際のプロセッサをそのメモリ インターフェイスから分離しようとしています。たとえば、古い TRS-80 には 12K の ROM があり、合計 16、32、または 48K の合計 RAM で構成できます。メモリ システムに関する私の最初のアイデアは、型クラスでした。
class MemorySystem memInternals addrType wordType where
-- | General memory fetch. This always returns a 'wordType' value,
-- even if the system's memory internals are byte addressable.
mfetch :: addrType -- ^ The address from which the instruction will be fetched
-> memInternals -- ^ The memory system
-> wordType -- ^ The fetched word
-- | Fetch a block of words from the memory system
mfetchN :: ( Unbox wordType
) =>
addrType -- ^ The address from which the instruction will be fetched
-> Int -- ^ Number of words to fetch
-> memInternals -- ^ The memory system
-> Vector wordType -- ^ The words fetched
明確化: 要点はMemorySystem
、命令デコーダ (TRS-80 の場合は Z80 命令デコーダ) がそのメモリ インターフェイスとは独立して動作できるようにすることですmfetch
。オペランド。したがって、memInternals
型クラス関数によって部分的に指定されたメモリ システムへのインターフェイスを実装する型です。
ポリモーフィックであることを許可しながら、つまり異なるメモリ構成を表すことを許可addrType
しwordType
ながら、制約する最良の方法はどのようにするかです。次のような関数にコンテキストを追加していることに気づきました。memInterals
memInternals
foo :: ( MemorySystem memSys Word16 Word8) =>
-> memSys
-> Word16
-> Word16
bar :: ( MemorySystem memSys Word16 Word8) =>
-> memSys
-> Word16
-> Word8
bar mem pc = ...
-- bar calls foo -> rigid type variable error...
これにより、ghc で多くの固定型変数エラーが発生します。
メモリ インターフェイスのファミリを適切に表現できる (型クラスまたはファミリを介して作用する) ように、MemorySystem
ポリモーフィズムの「正しい型」につながるa を表現するより良い方法はありますか?memInternals