🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
タプル

タプルは、順序付けされた複数の要素で構成される組の集合数詞です。元々は数学の概念ですが、PythonやML、Haskellなどのプログラミング言語にはタプルという名称のデータ型が用意されています。

OpenCV

OpenCV(オープンソースコンピュータービジョン)は、1999年にインテルが開発・公開したオープンソースのコンピュータビジョン向けのクロスプラットフォームライブラリです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

配列

配列は、各データの要素(値または変数)が連続的に並べられたデータ構造です。各配列は添え字(INDEX)で識別されています。

Q&A

3回答

841閲覧

数値が最大のタプルをタプルごと取り出したい

jenison

総合スコア2

タプル

タプルは、順序付けされた複数の要素で構成される組の集合数詞です。元々は数学の概念ですが、PythonやML、Haskellなどのプログラミング言語にはタプルという名称のデータ型が用意されています。

OpenCV

OpenCV(オープンソースコンピュータービジョン)は、1999年にインテルが開発・公開したオープンソースのコンピュータビジョン向けのクロスプラットフォームライブラリです。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

配列

配列は、各データの要素(値または変数)が連続的に並べられたデータ構造です。各配列は添え字(INDEX)で識別されています。

0グッド

0クリップ

投稿2021/01/20 10:24

前提・実現したいこと

数値が最大のタプルごとを取り出したい

発生している問題・エラーメッセージ

関数rectは画像から抽出した矩形領域の情報がタプルとして入っていて[x,y,width,height]の順に複数入っています。
ここから、widthが最大のタプルだけをprintしたいのですがどうすればいいのでしょうか?

該当のソースコード

python

1import cv2 2import numpy as np 3 4 5image = cv2.imread('適当な画像を絶対パスで記入してください') 6 7def find_rect_of_target_color(image): 8 hsv = cv2.cvtColor(image, cv2.COLOR_BGR2HSV_FULL) 9 h = hsv[:, :, 0] 10 s = hsv[:, :, 1] 11 mask = np.zeros(h.shape, dtype=np.uint8) 12 mask[((h < 180) | (h > 210)) & (s > 128)] = 255 13 contours, _ = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE) 14 rects = [] 15 for contour in contours: 16 approx = cv2.convexHull(contour) 17 rect = cv2.boundingRect(approx) 18 rects.append(np.array(rect)) 19 rect = max(rects, key=(lambda x: x[2] * x[3])) 20 print(rect) 21 return rects 22 23find_rect_of_target_color(image)

試したこと

自分で定義した関数rectは画像から抽出した矩形領域の情報が入っていて[x,y,width,height]の順に入っています。
ここから、widthが最大のタプルだけをprintしたいのですがどうすればいいのでしょうか?
上記のコードを実行するとたくさんのタプルがprintされてしまいます

rect = max(rects, key=(lambda x: x[2] * x[3]))
上記のコードでwidthが最大のタプルを引き出せると思っていたのですが、小さいタプルから大きいタプルに整列されただけでした。

補足情報(FW/ツールのバージョンなど)

ここのサイトを参考にしています。
https://qiita.com/odaman68000/items/ae28cf7bdaf4fa13a65b

ここにより詳細な情報を記載してください。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答3

0

operator を使いましょう。

Python

1>>> from operator import itemgetter 2>>> a = np.random.randint(1,10, (10, 2)) 3>>> a 4array([[4, 5], 5 [2, 5], 6 [8, 7], 7 [5, 1], 8 [6, 7], 9 [4, 8], 10 [6, 2], 11 [3, 6], 12 [8, 2], 13 [4, 3]]) 14>>> max(a, key=itemgetter(0)) 15array([8, 7])

投稿2021/01/20 10:56

A_kirisaki

総合スコア2853

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

rect = max(rects, key=(lambda x: x[2] * x[3]))

上記のコードでwidthが最大のタプルを引き出せると思っていたのですが、小さいタプルから大きいタプルに整列されただけでした。

この書き方で合っているはずです。ただし「widthが最大」ではなくwidth×height(=たぶん面積)が最大のものですが。

整列させるのはsortです。 書き間違えか、もしかしてどこかで、max = sortなどとしていたりしないでしょうか。

投稿2021/01/20 10:53

TakaiY

総合スコア13748

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

ひょっとして、表示されたものを誤解していませんか。

小さな画像で実行してみた結果を見ると

python

1>>> find_rect_of_target_color(image) 2[ 6 11 1 1] 3[ 0 11 6 18] 4[ 0 11 6 18] 5[16 6 7 23] 6[16 6 7 23] 7[array([ 6, 11, 1, 1]), array([ 0, 11, 6, 18]), array([ 2, 10, 1, 1]), array([16, 6, 7, 23]), array([10, 6, 3, 3])]

for文の中のprintの出力が最初の5行です。これはprint文を5回しているので当然です。
最後の行はfind_rect_of_target_colorの戻り値です。ファイルで実行した場合はこれは出ません。

やりたいことは以下なのかと思いますが、違っていたらこれを参考にして修正してください。

python

1import cv2 2import numpy as np 3 4 5image = cv2.imread('適当な画像を絶対パスで記入してください') 6 7def find_rect_of_target_color(image): 8 hsv = cv2.cvtColor(image, cv2.COLOR_BGR2HSV_FULL) 9 h = hsv[:, :, 0] 10 s = hsv[:, :, 1] 11 mask = np.zeros(h.shape, dtype=np.uint8) 12 mask[((h < 180) | (h > 210)) & (s > 128)] = 255 13 contours, _ = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE) 14 rects = [] 15 for contour in contours: 16 approx = cv2.convexHull(contour) 17 rect = cv2.boundingRect(approx) 18 rects.append(np.array(rect)) 19 return max(rects, key=(lambda x: x[2] * x[3])) 20 21print(find_rect_of_target_color(image))

なお、rectはtupleではなくndarrayです。

投稿2021/01/21 03:04

ppaul

総合スコア24670

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.36%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問