logo

パイソン | 2D 配列/リストを正しい方法で使用する

パイソン は、要素のコレクションを保存および操作できるリストと呼ばれる強力なデータ構造を提供します。 2 次元のリスト/配列を作成するためのさまざまな方法も提供します。ただし、これらの方法ではコードが複雑になり、追跡が非常に困難になる可能性があるため、これらの方法の違いを理解しておく必要があります。この記事では、Python で 2D 配列/リストを使用する正しい方法を検討します。

2D 配列/リストを正しい方法で使用する

2D 配列/リストを正しく使用するには、構造を理解し、要素にアクセスし、2 次元グリッド内のデータを効率的に操作する必要があります。構造化データまたはグリッドを操作する場合、2D 配列またはリストが便利です。 2D 配列は本質的にはリストのリストであり、行と列を含むテーブルのような構造を表します。



1-D リストの作成

Python では、線形シーケンス内の要素のコレクションを初期化するには、基本的なプロセスである 1D 配列を作成する必要があります。 Python には「1D 配列」と呼ばれる組み込みデータ構造はありませんが、同じ機能を実現できるリストを使用できます。 Python リストは動的で多用途であるため、1D 配列を表すのに最適です。まずは、0 で初期化されたサイズ N の 1 次元配列を作成する一般的な方法を見てみましょう。

単純なメソッドを使用した 1D リストの作成

Python の高度な機能や構成を使用せずにリストを手動で初期化し、値を設定することは、単純なメソッドを使用して 1D リストを作成することとして知られています。

Python3








偏微分記号ラテックス
N>=> 5> ar>=> [>0>]>*>N> print>(ar)>

>

>

出力

[0, 0, 0, 0, 0]>

リスト内包表記を使用した 1D リストの作成

ここでは空のリストに行数を乗算しているため、リスト全体がすべての要素が 0 で作成されます。

Python3




N>=> 5> arr>=> [>0> for> i>in> range>(N)]> print>(arr)>

>

>

出力

[0, 0, 0, 0, 0]>

2-D リストの作成

2D 配列/リストを正しく使用するには、構造を理解し、要素にアクセスし、2 次元グリッド内のデータを効率的に操作する必要があります。 2D 配列の使用をマスターすると、複雑なデータを処理し、さまざまな操作を効率的に実行する能力が大幅に向上します。

を使用して 2D リストを作成する 素朴な方法

ここでは列数を乗算しているため、列数と同じサイズの 1 次元リストを取得し、それを行数と乗算して 2 次元リストが作成されます。

ラテックスのフォントサイズ

Python3




rows, cols>=> (>5>,>5>)> arr>=> [[>0>]>*>cols]>*>rows> print>(arr)>

>

>

出力

[[0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]]>

注記: この方法を使用すると、予期しない動作が発生する場合があります。このメソッドでは、各行が同じ列を参照します。つまり、配列の 1 つの要素だけを更新した場合でも、配列内の同じ列が更新されます。

パイソン




rows, cols>=> (>5>,>5>)> arr>=> [[>0>]>*>cols]>*>rows> print>(arr,>'before'>)> arr[>0>][>0>]>=> 1> # update only one element> print>(arr,>'after'>)>

>

>

出力

([[0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]], 'before') ([[1, 0, 0, 0, 0], [1, 0, 0, 0, 0], [1, 0, 0, 0, 0], [1, 0, 0, 0, 0], [1, 0, 0, 0, 0]], 'after')>

を使用して 1D リストを作成する リストの内包表記

ここでは基本的にリスト内包表記の概念を使用し、リスト内のリストにループを適用して、2 次元リストを作成します。

Python3




私のコンピュータの画面サイズはどれくらいですか
rows, cols>=> (>5>,>5>)> arr>=> [[>0> for> i>in> range>(cols)]>for> j>in> range>(rows)]> print>(arr)>

>

>

出力

[[0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]]>

を使用して 1D リストを作成する 空のリスト

ここでは、多数の列の要素としてゼロを追加し、次にこの 1 次元リストを空の行リストに追加して、2 次元リストを作成します。

Python3




arr>=>[]> rows, cols>=>5>,>5> for> i>in> range>(rows):> >col>=> []> >for> j>in> range>(cols):> >col.append(>0>)> >arr.append(col)> print>(arr)>

>

>

出力

[[0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]]>

2D 配列の初期化

提供されたコードは、2D 配列を初期化するための 2 つの異なるアプローチを示しています。 パイソン 。まず、配列arr>は 2D リスト内包表記を使用して初期化され、各行は次のように作成されます。[0, 0, 0, 0, 0]>。配列全体が同じ内部リストへの参照のリストとして作成されるため、エイリアシングが発生します。 1 つの行の要素に加えられた変更はすべての行に反映されます。次に、コードは、ネストされたリスト内包表記を使用して 2D 配列を作成する別のアプローチを示します。arr>。この方法では、行ごとに新しいリストを作成することでエイリアスを回避し、適切な 2D 配列を生成します。

フルフォームpvr

Python3




# Python 3 program to demonstrate working> # of method 1 and method 2.> rows, cols>=> (>5>,>5>)> # method 2 1st approach> arr>=> [[>0>]>*>cols]>*>rows> # lets change the first element of the> # first row to 1 and print the array> arr[>0>][>0>]>=> 1> for> row>in> arr:> >print>(row)> # method 2 2nd approach> arr>=> [[>0> for> i>in> range>(cols)]>for> j>in> range>(rows)]> # again in this new array lets change> # the first element of the first row> # to 1 and print the array> arr[>0>][>0>]>=> 1> for> row>in> arr:> >print>(row)>

>

>

出力

[1, 0, 0, 0, 0] [1, 0, 0, 0, 0] [1, 0, 0, 0, 0] [1, 0, 0, 0, 0] [1, 0, 0, 0, 0] [1, 0, 0, 0, 0] [0, 0, 0, 0, 0] [0, 0, 0, 0, 0] [0, 0, 0, 0, 0] [0, 0, 0, 0, 0]>

説明:

最初の行の最初の要素のみが 1 に変更されることが期待されますが、メソッド 2a ではすべての行の最初の要素が 1 に変更されます。この奇妙な機能は、Python が浅いリストを使用しているためであり、それを理解しようとします。
方法 1a では、Python は 5 つの整数オブジェクトを作成せず、1 つの整数オブジェクトのみを作成します。また、配列 arr のすべてのインデックスは、示されているように同じ int オブジェクトを指します。

0 番目のインデックスを別の整数、たとえば 1 に割り当てると、値 1 を持つ新しい整数オブジェクトが作成され、次に示すように 0 番目のインデックスがこの新しい int オブジェクトを指すようになります。

同様に、arr = [[0]*cols]*rows として 2 次元配列を作成すると、本質的に上記の類似性を拡張したことになります。

  1. 整数オブジェクトは 1 つだけ作成されます。
  2. 単一の 1d リストが作成され、そのすべてのインデックスはポイント 1 の同じ int オブジェクトを指します。
  3. さて、arr[0]、arr[1]、arr[2]…。 arr[n-1] はすべて、上記のポイント 2 と同じリスト オブジェクトを指します。

上記の設定は、以下の画像で視覚化できます。

ここで、arr の最初の行の最初の要素を arr[0][0] = 1 に変更してみましょう。

  • arr[0] は、上で作成した単一のリスト オブジェクトを指します (arr[1]、arr[2] …arr[n-1] もすべて同じリスト オブジェクトを指すことを思い出してください)。
  • arr[0][0] を割り当てると、値 1 を持つ新しい int オブジェクトが作成され、arr[0][0] はこの新しい int オブジェクトを指すようになります (arr[1][0]、arr も同様です)。 [2][0] … arr[n-1][0])

これは下の画像ではっきりとわかります。

したがって、このように 2 次元配列が作成される場合、配列のすべての行によって参照される整数オブジェクトとリスト オブジェクトは基本的に 1 つだけであるため、特定の行の値を変更するとすべての行に影響します。

ご想像のとおり、このような浅いリストの使用によって引き起こされるエラーを追跡するのは困難です。したがって、2次元配列を宣言するより良い方法は次のとおりです。

Python3




rows, cols>=> (>5>,>5>)> print>([[>0> for> i>in> range>(cols)]>for> j>in> range>(rows)])>

>

>

出力

[[0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0], [0, 0, 0, 0, 0]]>

このメソッドは、メソッド 2a とは異なり、5 つの個別のリスト オブジェクトを作成します。これを確認する 1 つの方法は、2 つのオペランドが同じオブジェクトを参照しているかどうかを確認する「is」演算子を使用することです。

SQL複数テーブル選択

Python3




rows, cols>=> (>5>,>5>)> # method 2 2nd approach> arr>=> [[>0> for> i>in> range>(cols)]>for> j>in> range>(rows)]> # check if arr[0] and arr[1] refer to> # the same object> print>(arr[>0>]>is> arr[>1>])># prints False> # method 2 1st approach> arr>=> [[>0>]>*>cols]>*>rows> # check if arr[0] and arr[1] refer to the same object prints True because there is only one> #list object being created.> print>(arr[>0>]>is> arr[>1>])>

>

>

出力

False True>