Python 3.2.2でctypesを使用して、いくつかのCデータ構造をカプセル化しています。最終的な目標は、構造体のデータコンテンツが変更されたときに、C構造体の通知をラップするオブジェクトを作成できるようにすることです。
代表的なコード:
from ctypes import *
class Comm(Structure):
def __init__(self):
self.attributes_updated = False
def __setattr__(self, name, value):
super(Comm, self).__setattr__('attributes_updated', True)
super(Comm, self).__setattr__(name, value)
class MyCStruct(Comm):
_fields_ = [('number', c_int),
('array', c_int*5)]
def __init__(self):
Comm.__init__(self)
これは、「数値」などの単純なデータ属性に最適です。
>>> s = MyCStruct()
>>> s.attributes_updated
False
>>> s.value = 123
>>> s.attributes_updated
True
__setattr__
属性へのインデックス表記を介したアクセスに対しては呼び出されないため、
配列であるC構造体のメンバーの属性array
をオーバーライドしたいと思います。__setitem__
おそらく、その時点で、包含オブジェクトの変数を変更できるように、包含オブジェクトへの参照を含める必要がありますがattributes_updated
、配列属性へのアクセスを便利な方法でトラップできるようにはなりません。単純な属性へのアクセスをトラップできること。_fields_
ctypesが変数を介して作成するインデックス可能なオブジェクトでこれを行う方法はありますか?オーバーライドすることは可能__setitem__
ですs.array
か?これを行うためのより良い方法があるでしょうか?
理想的には、これは起こります:
>>> s = MyCStruct()
>>> s.attributes_updated
False
>>> s.array[2] = 456
>>> s.attributes_updated
True
フォローアップの質問のために編集します:
多次元配列はどうですか?
class MyCStruct(Comm):
_fields_ = [('number', c_int),
('array', (c_int*5)*2]
私は誤って以下の答えを期待していました。これは、1次元配列で見事に機能し、任意にネストされた配列でも同じことを行います。プロキシオブジェクトを再帰的に生成して、複数の次元を持つ配列に対して同じことを行う方法があるはずです、そうですか?構文は私を逃れます。