私は GeekforGeeks Webサイトのチュートリアル で作業しており、board[x,y]
を使用して配列内のポイントをチェックしていることがわかりました。これはうまくいくとは思いませんが、プログラムを実行すると、すべてが期待どおりに進みます。
上記で概説した方法と、慣れ親しんだ方法(board[x][y]
)を使用して小さなコード例を実行してみましたが、コードを実行するとTypeError: list indices must be integers or slices, not Tuple
が表示されます
私のコード:
board = [[1,1,1], [1,2,2], [1,2,2]]
win = 'True'
if board[1][1] == 2:
win = 'True by normal standards'
print(win)
if board[1, 1] == 2:
win = 'True by weird standards'
print(win)
print(win)
彼らのコード:
def row_win(board, player):
for x in range(len(board)):
win = True
for y in range(len(board)):
if board[x, y] != player:
win = False
continue
if win == True:
return(win)
return(win)
誰かがboard[x,y]
が機能する理由と、正確には何が起こっているのかを私に説明できますか?リストを作成する以外は、これまで見たことがないので、概念的には把握していません。
彼らはNumPyを使用しているのでそれを行うことができ、それによってエラーはスローされません。
>>> a = np.array([[1,1,1], [1,2,2], [1,2,2]])
>>> a[1,1]
2
>>> # equivalent to
>>> a = [[1,1,1], [1,2,2], [1,2,2]]
>>> a[1][1]
2
>>>
彼らが使用しているオブジェクト(この場合はnumpy配列)が__getitem__
方法。このおもちゃの例を見てください:
class MyArray:
def __init__(self, arr):
self.arr = arr
def __getitem__(self, t):
return self.arr[t[0]][t[1]]
myarr = MyArray([[1,1,1], [1,2,2], [1,2,2]])
print(myarr[0,1])
これは実際にはbase Python=(例のように)では機能しません。コードを実行すると、Pythonが例外をスローします: 'TypeError:リストインデックスはタプルではなく整数またはスライス。
1, 1
に渡されたboard
はタプルとして解釈され、ボードには整数またはスライスでインデックスを付ける必要があるため、これは機能しません。
ただし、board
が何らかのタイプの配列のようなデータ構造であり、開発者がタプルを使用したインデックス付けのサポートを実装している場合、これは機能します。この例は、numpy
の配列です。
board[x, y]
構文は、numpy配列に適用されている可能性があります。これは、行/列のインデックス付きスライス操作を実装するためにこの構文を受け入れます。これらの例を見てください:
>>> x = np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) # creates 2D array
>>> x
array([[1, 2, 3],
[4, 5, 6],
[7, 8, 9]])
>>> x[1] # get second row (remember, index starts at 0)
array([4, 5, 6])
>>> x[:, 2] # get third column
array([3, 6, 9])
>>> x[1, 2] # get element on second row, third column
6
>>> x[1][2] # same as before but with non-broadcasting syntax (i.e. works for lists as you are used to)
6
>>> x[1, 0:2] # get first two elements of second row
array([4, 5])
>>> x[0:2, 0:2] # subsets the original array, "extracting" values from the first two columns/rows only
array([[1, 2],
[4, 5]])
もちろん、my_list[x, y]
は、x, y
は実際にはタプル(x, y)
、そして通常のリストはタプルをインデックス値として使用できません。
それらのboard
は_numpy.ndarray
_またはそれをラップする何らかの型であるため、たとえば_pandas.DataFrame
_ _board[x,y]
_ is pandas =ベースPythonではなく、2Dインデックス。
type(board)
を実行する必要があります。または、board
を作成して初期化する行を示します。
また、「プログラムを実行すると、すべてが期待どおりに進む」と言う場合は、インタラクティブモード(_python -i
_)で実行する必要があります。その後、type(board)
(またはiPython/jupyter type whos
変数とそのタイプのリストを表示します)
Pythonでは、[]
は__getitem__
、これは簡単に書き換えることができます。
そして、1, 2
in pythonはタプルを提供します。はい、本当に必要ありません()
空でないタプルを作成します。
ですから、Numpyはこれを非常に簡単に行うことができます。
In [1]: 1, 1
Out[1]: (1, 1)
In [2]: type(_)
Out[2]: Tuple
In [3]: a = {(1, 1): 3}
In [4]: a[1, 1]
Out[4]: 3
In [5]: a[(1, 1)]
Out[5]: 3
In [6]: class NumpyArray(list):
...: def __getitem__(self, index):
...: if isinstance(index, Tuple) and len(index) == 2:
...: return self[index[0]][index[1]]
...: return super().__getitem__(index)
...:
In [7]: b = NumpyArray([[0, 1], [2, 3]])
In [8]: b[1, 1]
Out[8]: 3
以下のコードを使用して、独自のiPythonを試すことができます。
class NumpyArray(list):
def __getitem__(self, index):
if isinstance(index, Tuple) and len(index) == 2:
return self[index[0]][index[1]]
return super().__getitem__(index)
b = NumpyArray([[0, 1], [2, 3]])
b[1, 1]