# 6 `mmap` -- メモリマップファイル

メモリにマップされたファイルオブジェクトは、 文字列とファイルオブジェクトの両方のように振舞います。 しかし通常の文字列オブジェクトとは異なり、これらは可変です。 文字列が期待されるほとんどの場所でmmapオブジェクトを利用できます。 例えば、メモリマップファイルを探索するために `re`モジュールを使うことができます。 それらは可変なので、 `obj[index] = 'a'` のように文字を 変換できますし、スライスを使うことで `obj[i1:i2] = '...'` のように 部分文字列を変換することができます。 現在のファイル位置をデータの始めとする読込みや書込み、 ファイルの異なる位置へ`seek()`することもできます。

メモリマップファイルはUnix上とWindows上とでは異なる `mmap()`関数によって作られます。 いずれの場合も、開いたファイルのディスクリプタを、 更新のために提供しなければなりません。 すでに存在するPythonファイルオブジェクトをマップしたい場合は、 filenoパラメータのための現在値を手に入れるために、 `fileno()`メソッドを使用して下さい。 そうでなければ、ファイル・ディスクリプタを直接返す`os.open()`関数 (呼び出すときにはまだファイルが閉じている必要があります)を使って、 ファイルを開くことができます。

関数のUnixバージョンとWindowsバージョンのために、 オプションのキーワード・パラメータとしてaccessを指定する ことになるかもしれません。 accessは3つの値の内の1つを受け入れます。 `ACCESS_READ`は読み込み専用、 `ACCESS_WRITE`は書き込み可能、 `ACCESS_COPY`はコピーした上での書き込みです。 accessはUnixとWindowsの両方で使用することができます。 accessが指定されない場合、Windowsのmmapは書き込み可能マップを返します。 3つのアクセス型すべてに対する初期メモリ値は、 指定されたファイルから得られます。 `ACCESS_READ`を割り当てたメモリマップは `TypeError`例外を送出します。 `ACCESS_WRITE`を割り当てたメモリマップは メモリと元のファイルの両方に影響を与えます。 `ACCESS_COPY`を割り当てたメモリマップは メモリに影響を与えますが、元のファイルを更新することはありません。 バージョン 2.5 で 変更 された仕様: 無名メモリ(anonymous memory)をマップするためにはfilenoとして -1 を渡して長さを与えてください

`mmap`( | fileno, length[, tagname[, access]])

  (Windows)バージョンはファイルハンドルfilenoによって 指定されたファイルからlengthバイトをマップして、 mmapオブジェクトを返します。 lengthが現在のファイルサイズより大きな場合、ファイルサイズは lengthを含む大きさにまで拡張されます。 lengthが`0`の場合、マップの最大の長さは Windowsが空ファイルで例外を起こす(Windowsでは空のマップを作成すること ができません。)ことを除いては、 `mmap()`が呼ばれたときのファイルサイズになります。

  tagnameは、`None`以外で指定された場合、 マップのタグ名を与える文字列となります。 Windowsは同じファイルに対する様々なマップを持つことを可能にします。 既存のタグの名前を指定すればそのタグがオープンされ、 そうでなければこの名前の新しいタグが作成されます。 もしこのパラメータを省略したり`None`を与えたりしたならば、 マップは名前なしで作成されます。 タグ・パラメータの使用の回避は、あなたのコードをUnixとWindowsの間で 移植可能にしておくのを助けてくれるでしょう。

`mmap`( | fileno, length[, flags[, prot[, access]]])

  (Unix)バージョンは、ファイル・ディスクリプタ filenoに よって指定されたファイルからlengthバイトをマップし、 mmapオブジェクトを返します。lengthが`0`の場合、 そのマップの最大長が現在のファイルサイズになります。

  flagsはマップの種類を指定します。 `MAP_PRIVATE`はプライベートなcopy-on-write(書込み時コピー) のマップを作成します。 従って、mmapオブジェクトの内容への変更はこのプロセス内にのみ有効です。 `MAP_SHARED`はファイルの同じ領域をマップする他のすべてのプロセス と共有されたマップを作成します。 デフォルトは`MAP_SHARED`です。

  protが指定された場合、希望のメモリ保護を与えます。 2つの最も有用な値は、`PROT_READ`と`PROT_WRITE`です。 これは、読込み可能または書込み可能を指定するものです。 protのデフォルトは`PROT_READ | PROT_WRITE`です。

  accessはオプションのキーワード・パラメータとして、 flagsとprotの代わりに指定してもかまいません。 flags,protとaccessの両方を指定することは間違っています。 このパラメーターを使用法についての情報は、 accessの記述を参照してください。

メモリマップフィイルオブジェクトは以下のメソッドをサポートしています:

`close`( | )

  ファイルを閉じます。 この呼出しの後にオブジェクトの他のメソッドの呼出すことは、 例外の送出を引き起こすでしょう。

`find`( | string[, start])

  オブジェクト内で部分文字列stringが見つかった場所の最も小さい インデックスを返します。 失敗したとき`-1`を返します。 startは探索を始めたい場所のインデックスで、デフォルトは0です。

`flush`( | [offset, size])

  ファイルのメモリコピー内での変更をディスクへフラッシュします。 この呼出しを使わなかった場合、オブジェクトが破壊される前に 変更が書き込まれる保証はありません。 もしoffsetとsizeが指定された場合、与えられたバイトの範囲の 変更だけがディスクにフラッシュされます。 指定されない場合、マップ全体がフラッシュされます。

`move`( | dest, src, count)

  オフセットsrcからインデックスdestへcountバイトだけ コピーします。 もしmmapが`ACCESS_READ`で作成されていた場合、 `TypeError`例外を送出します。

`read`( | num)

  現在のファイル位置からnumバイトの文字列を返します。 ファイル位置は返したバイトの分だけ後ろの位置へ更新されます。

`read_byte`( | )

  現在のファイル位置から長さ1の文字列を返します。 ファイル位置は1だけ進みます。

`readline`( | )

  現在のファイル位置から次の新しい行までの、1行を返します。

`resize`( | newsize)

  マップと元ファイルのサイズを変更します。 もしmmapが`ACCESS_READ`または`ACCESS_COPY`で 作成されたならば、マップのリサイズは`TypeError`例外を送出します。

`seek`( | pos[, whence])

  ファイルの現在位置をセットします。 whence引数はオプションであり、デフォルトは`0`(絶対位置)です。 その他の値として、`1`(現在位置からの相対位置)と `2`(ファイルの終わりからの相対位置)があります。

`size`( | )

  ファイルの長さを返します。 メモリマップ領域のサイズより大きいかもしれません。

`tell`( | )

  ファイル・ポインタの現在位置を返します。

`write`( | string)

  メモリ内のファイル・ポインタの現在位置からstringのバイト列を 書き込みます。 ファイル位置はバイト列が書き込まれた後の位置へ更新されます。 もしmmapが`ACCESS_READ`で作成されていた場合、 書き込み時に`TypeError`例外が送出されるでしょう。

`write_byte`( | byte)

  メモリ内のファイル・ポインタの現在位置から 単一文字の文字列byteを書き込みます。 ファイル位置は`1`だけ進みます。 もしmmapが`ACCESS_READ`で作成されていた場合、 書き込み時に`TypeError`例外が送出されるでしょう。