実現したいこと
あるクラスのクラス変数に、そのクラスが属しているモジュールからだけでなく他のモジュールからもアクセスしたい。
前提
クラス変数にはそのクラス内のメソッドを介して書き込み、読出しを行ない、クラスの外からは直接クラス変数にアクセスしないようにしています。
最終的にはクラス変数に__を付けて外部から隠蔽する予定です。
複数のモジュールで構成されているシステムで、どのモジュールからもクラス変数を読み書きできるようにするにはどうすればよいのでしょうか。特別な書き方があるのでしょうか。よろしくご教示ください。
発生している問題・エラーメッセージ
クラスが属しているモジュール(モジュール1)の中でだけクラス変数を読み書きしたときは、クラス変数が共有され書き換えた内容が保持されています。
しかしその書き換えたクラス変数を他のモジュール(モジュール2)から読み出すとクラス変数は書き換えられておらず定義した時の初期値のままになっています。
逆にモジュール2からクラス変数を書き換えた場合、モジュール2およびクラスが属するモジュール1のどちらでで読み出してもクラス変数が正しく書き換わっています。
とくにエラーメッセージは出ていません
該当のソースコード
Python
1以下の二つのモジュール作り、それぞれ実行した 2 3コード 4```# モジュール1(module_1.py クラスが属するモジュール) 5import module_2 as md2 6 7class Cls1: 8 s = ['A', 'B'] # クラス変数 9 10 def read_1(self): # クラス変数をmodule_1で読む 11 print(Cls1.s) 12 # print(self.__class__.s) 13 14 def wr_1(self, i, d): # クラス変数を書き換える 15 Cls1.s[i] = d 16 # self.__class__.s[i] = d 17 18if __name__ == '__main__': 19 c1 = Cls1() 20 21 c1.read_1() # module_1で読む:結果['A', 'B']初期値 22 md2.read_2() # module_2で読む:結果['A', 'B']初期値 23 24 c1.wr_1(0, 'a') # module_1でクラス変数を書き換え 25 c1.read_1() # module_1で読む:結果['a', 'B']書き換えOK 26 md2.read_2() # module_2で読む:結果['A', 'B']共有NG 27 28 29# モジュール2(module_2.py クラス変数とは別のモジュール) 30import module_1 as md1 31 32def read_2(): # クラス変数をmodule_2で読む 33 print(md1.Cls1.s) 34 # c1 = md1.Cls1() 35 # print(c1.__class__.s) 36 37if __name__ == '__main__': 38 c1 = md1.Cls1() 39 40 c1.read_1() # module_1で読む:結果['A', 'B']初期値 41 read_2() # module_2で読む:結果['A', 'B']初期値 42 43 c1.wr_1(1, 'b') # module_2からmodule_1のクラス変数を書換え 44 c1.read_1() # module_1で読む:結果['A', 'b']書換えOK 45 read_2() # module_2で読む:結果['A', 'b']共有OK 46
試したこと
上記のソースコードのモジュール1を実行すると、変数を書き換えた後に読み出したクラス変数がモジュール1とモジュール2で違う。モジュール1で読むとクラス変数は書き換わっているのに、モジュール2で読むと初期値のままである。
ところがモジュール2を実行してモジュール2からモジュール1のクラス変数を書き換えると、モジュール1、モジュール2のどちらで読んでもクラス変数はちゃんと書き換わっている。
上記のほかに以下のことを試しました。
A.クラスのメソッドをクラスメソッドに変えても結果は同じでした。
B.クラスのインスタンス経由でメソッドを呼んだときにメソッド内でコメントアウトしてあるように
self.class.s
の形式で書き換え、読出しを行なっても結果は同じでした。
C.全く別のモジュールにクラスを作り、その中にクラス変数だけを入れ、モジュール1とモジュール2からアクセスすると共有が正常に行われました。
ただこれではグローバル変数と同じで、クラス変数として置く意味がないように思います。
補足情報(FW/ツールのバージョンなど)
とくにありません### ヘディングのテキスト
回答2件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2024/04/09 13:17
2024/04/09 14:22 編集