『Python数値計算ノート』ではアフィリエイトプログラムを利用して商品を紹介しています。

numpy.unique()で重複要素を削除した配列を生成する

numpy.unique()

numpy.unique() は受け取った配列から重複要素削除してユニークな要素だけで構成される配列を返します (Python の set() に相当する関数です)。

numpy.unique(arr, return_index=False, return_inverse=False,
return_counts=False, axis=None)

最初にオプション引数なしで 1 次元配列を渡してみます。

# NUMPY_UNIQUE_01

# In[1]

import numpy as np

# 配列xを定義
x = np.array([0, 5, 1, 3, 5, 0, 2])

# xの重複要素を取り除く
a = np.unique(x)

print(a)
# [0 1 2 3 5]

return_index を True に設定すると、ユニーク配列に加えて、各要素の抽出位置 (インデクス) を示す配列も返します。

# In[2]

# ユニーク配列と、抽出要素のインデクスを取得
b = np.unique(x, return_index=True)

print(b)
# (array([0, 1, 2, 3, 5]), array([0, 2, 6, 3, 1], dtype=int64))

この実行結果は、もとの配列の [0, 2, 6, 3, 1] の位置から要素を取ってユニーク配列 [0, 1, 2, 3, 5] が生成されたことを意味しています。
 
return_inverse に True を渡すと、ユニーク配列に加えて、ユニーク配列をもとの配列に復元するインデクス配列を取得します。

# In[3]

# ユニーク配列と、もとの配列に復元するインデクス配列を取得
c, d = np.unique(x, return_inverse=True)

print(c)
print(d)
# [0 1 2 3 5]
# [0 4 1 3 4 0 2]

すなわち、c[d] でもとの配列 x を復元できます。

# In[4]

# 配列xを復元
print(c[d])
# [0 5 1 3 5 0 2]

return_counts に True を渡すと、ユニーク配列に加えて、もとの配列にそれぞれの要素が何個ずつ含まれていたかを示す配列を返します。

# In[5]

# ユニーク配列に加えて、
# もとの配列に各要素が何個ずつ含まれていたかを示す配列を取得
e, f = np.unique(x, return_counts=True)

print(e)
print(f)

# [0 1 2 3 5]
# [2 1 1 1 2]

axis を指定せずに numpy.uniqe() に 2 次元配列を渡すと、1 次元にフラット化されたユニーク配列が返ります。

# NUMPY_UNIQUE_02

# In[1]

import numpy as np

# 配列yを定義
y = np.array([[0, 1, 1],
              [0, 1, 1],
              [1, 0, 1]])

# yをフラットにしてユニーク配列を生成
g = np.unique(y)

print(g)
# [0 1]

axis=0 を渡すと、重複する行を省いて新しい配列を生成します。

# In[2]

# 行が重複しない配列を生成
h = np.unique(y, axis=0)

print(h)
# [[0 1 1]
#  [1 0 1]]

axis=1 を渡すと、重複する列を取り除いた新しい配列を生成します。

# In[3]

# 配列zを作成
z = np.array([[9, 9, 0, 1],
              [0, 0, 1, 1],
              [9, 9, 0, 0]])

# 列が重複しな配列を生成
i = np.unique(z, axis=1)

print(i)
# [[0 1 9]
#  [1 1 0]
#  [0 0 9]]

return_index=True と axis=1 を組合わせると、重複列を取り除いたユニーク配列と、抽出した列のインデクス配列をタプルで返します。

# In[4]

# ユニーク配列と、抽出した列のインデクス配列を取得
j, k = np.unique(z, return_index=True, axis=1)

print(j)
print(k)

# [[0 1 9]
#  [1 1 0]
#  [0 0 9]]

# [2 3 0]

 

コメント

  1. HNaito より:

    In[2] プログラムとその実行結果が分離されていません。
    In[2] プログラムの実行結果の dtype=int32 は、Google Colabでは表示されませんでした。

    • あとりえこばと より:

      申し訳ないです。実行結果を囲む html タグがおかしかったです。
      修正して分離しておきました。
      確かに Google Colab では dtype が表示されませんね。x を生成するときに dtype を ‘int32’ などにすると、戻り値のユニーク配列のほうに dtype が含まれていました (Jupyter ではインデックス配列のほうに添えられます)。

      import numpy as np
      x = np.array([0, 5, 1, 3, 5, 0, 2], dtype='int32')
      b = np.unique(x, return_index=True)
      print(b)
      # (array([0, 1, 2, 3, 5], dtype=int32), array([0, 2, 6, 3, 1]))
      


      unique() 関数に渡した整数配列がデフォルトの型 (int64) だと表示されない仕組みになっているかもしれません。以下のコードを Jupyter Notebook で試してみると、dtype が int64 になってました (後で記事を修正しておきます)。

      
      import numpy as np
      x = np.array([0, 5, 1, 3, 5, 0, 2])
      b = np.unique(x, return_index=True)
      print(b)
      # (array([0, 1, 2, 3, 5]), array([0, 2, 6, 3, 1], dtype=int64))


      古い記事なので、NumPy のバージョンアップに伴う変更があったかもしれませんし、この記事を書いた時は 32 bit 版 Python を使っていたので、その影響かもしれません。ちなみに、現在の私の Jupyter Notebook の環境は以下の通りです。
      Python 3.9.9
      NumPy 1.21.4
      Google Colab は現時点 (2023.2.18) で次の環境が提供されているようです。
      Python 3.8.10
      NumPy 1.21.6