2011-01-03 13 views
1

にちょっとすべて、私はテーブルが、非常に奇妙な何かのようなものを構築するために辞書を使用するクラスが起こっされていることを確認しようとして .. HERESに私のコード原因不明のpythonの辞書の問題

class dbase: 
    def __init__(self): 
     self.rows = {} 
     self.cols = {} 
    def addrow(self, name): 
     self.rows[name] = self.cols 
    def addcol(self, name): 
     for x in self.rows: 
      self.rows[x][name] = None 
    def printit(self): 
     for x in self.rows: 
      print x, self.rows[x] 
a = dbase() 
a.addrow("coke") 
a.addcol("price") 
a.printit() 
a.addrow("sprite") 
a.printit() 

もの。私のプログラムはスプライト行を "価格"の値を持つ内側の辞書を持っているものとして印刷しますが、私のプログラムではどこにも書きません。self.cols ["price"] = None スプライトのaddrow関数は、 ? ありがとうございました

+2

http://python.net/~goodger/projects/pycon/2007/idiomatic/handout.html#other-languages-have-variablesすべての 'self.rows [x]'は同じオブジェクト 'self .cols'。 – jfs

+1

"私のプログラムではどこにいたのですか?' self.cols ["price"] = None' "はい、あります。 self.rows [x] [name] = None'はself.rows [x]が以前にself.colsに設定されているため正確に言います。 –

+0

新しいスタイルのクラスを使用 – Ant

答えて

2

の各値にはself.colsが割り当てられているため、シェアは同じ辞書をキーとして割り当てられます。 self.rows[x]を変更した場合、は同じオブジェクトであるため、self.rows[y]も変更します。同様に、self.rows[z]の値としてself.colsを再度追加すると、同じオブジェクトなので、すべて同じ内容になります。

それぞれの行に別々の空のdictを作成する場合は、には{}を割り当てます。

しかし、あなたは本当に最初にこのためのクラスを必要としません。それは自然にPythonで直接行われる何かのためのカスタムインターフェイスを使用することにあなたを押し込むだけです。あなたはおそらくcollections.defaultdictを探しているはずです。

1

a.addcol("price")に電話すると、コードはself.rows[x][name]に変更され、Noneと等しくなります。

self.colsは、dict {'price': None}に等しくなるように設定されます。 self.rows[x]はそれぞれself.colsに設定されているため、毎回同じdictが出力されます。

4

ワウ。これは私が見た中で最もメージャーなコードです。行を追加すると、他のすべての列にある同じ辞書を追加するだけで済みます。私はあなたが行の列を設定すると、あなたは常にself.colsを参照してください

def addrow(self, name): 
    self.rows[name] = {} 
0

を意味だと思う

def __init__(self): 
    self.rows = {} 
    self.cols = {} 
def addrow(self, name): 
    self.rows[name] = self.cols 

- Pythonは参照のようにこれを処理するので、あなたはそれを更新し、それを更新し、いつでもその参照を指すすべてのもの。

行ごとに異なる列のセットが必要な場合は、その都度適切な値に初期化する必要があります。

0

いつも同じ辞書インスタンスを再利用しています。

def addrow(self, name): 
    self.rows[name] = self.cols 

Pythonは変数の点でJavaと似ていますが、各名前は単なるオブジェクトインスタンスへの参照に過ぎません。変数の割り当てがほとんど常にを意味するCのようなものではありません。の値をコピーします。

あなたは、行と列のための間に合わせのn-テーブルクラスを作成する場合は、例えば、defaultdictの使用を作ることができる。これを行うには

from collections import defaultdict 

class RowsAndColumns: 
    def __init__(self): 
     self._rows = defaultdict(dict) 

    def get(self, row, col): 
     return self._rows[row][col] 

    def set(self, row, col, value): 
     self._rows[row][col] = value 

matrix = RowsAndColumns() 
matrix.set("Coke", "Price", 1.99) 
print matrix.get("Coke", "Price") # 1.99 
print matrix.get("Pepsi", "Price") # KeyError "Price" 
0

最も簡単な方法は、ちょうど持っていることです辞書のリスト。このように:

# A new "database" 
dbase = [] 
# Adding a new "row". 
dbase.append({}) 
# Adding columns to a specific row: 
dbase[0]['newcol'] = "The value" 
# Retrieving a colum from a row which will raise a KeyError if the column doesn't exist: 
dbase[0]['newcol'] 
# Retrieving a colum from a row which will return None if the column doesn't exist: 
dbase[0].get('anothercol') 

また、DefaultDictを見ることができますが、標準の辞書とオブジェクトがどのように最初に機能するかを知ることがより効果的だと思います。

関連する問題