質問をすることでしか得られない、回答やアドバイスがある。

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

新規登録して質問してみよう
ただいま回答率
85.48%
Python

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

Q&A

解決済

2回答

2350閲覧

PythonのTkinterで違うファイルから関数をインポートしたら、エラーが出て実行できなくなる

gymgym

総合スコア97

Python

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

0グッド

1クリップ

投稿2018/01/18 01:49

Python

1import cv2 2import random 3import pyautogui 4import pandas as pd 5import os 6from tkinter import ttk 7from tkinter import * 8from datetime import datetime 9#from classfy02 import input_data 10 11pyautogui.doubleClick(86,94) 12 13zyan_slide = ['paa.png', 'guu.png', 'tyoki.png'] 14q_slide = ['kati.png', 'make.png', 'hikiwake.png'] 15 16data_time = [] 17zyan, q = [],[] 18 19random.shuffle(zyan_slide) 20random.shuffle(q_slide) 21 22que_list, task_list = [], [] 23 24# 注視画像 25img = cv2.imread('cross.png') 26cv2.namedWindow('screen', cv2.WINDOW_NORMAL) 27cv2.setWindowProperty('screen', cv2.WND_PROP_FULLSCREEN, cv2.WINDOW_FULLSCREEN) 28cv2.imshow('screen', img) 29cv2.waitKey(1000) 30 31time = datetime.now() 32data_time.append(time) 33 34# 問題提示 35 36img = cv2.imread(q_slide[0]) 37cv2.namedWindow('screen', cv2.WINDOW_NORMAL) 38cv2.setWindowProperty('screen', cv2.WND_PROP_FULLSCREEN, cv2.WINDOW_FULLSCREEN) 39cv2.imshow('screen', img) 40cv2.waitKey(2000) 41img = cv2.imread(zyan_slide[0]) 42cv2.namedWindow('screen', cv2.WINDOW_NORMAL) 43cv2.setWindowProperty('screen', cv2.WND_PROP_FULLSCREEN, cv2.WINDOW_FULLSCREEN) 44cv2.imshow('screen', img) 45cv2.waitKey(2000) 46 47# グー:0、チョキ:1、パー:2 48if(zyan_slide[0]=='guu.png' and q_slide[0] == 'hikiwake.png' or zyan_slide[0]=='tyoki.png' and q_slide[0] == 'kati.png' or zyan_slide[0]=='paa.png' and q_slide[0] == 'make.png'): 49 zyan.append(0) 50elif(zyan_slide[0]=='tyoki.png' and q_slide[0] == 'hikiwake.png' or zyan_slide[0]=='paa.png' and q_slide[0] == 'kati.png' or zyan_slide[0]=='guu.png' and q_slide[0] == 'make.png'): 51 zyan.append(1) 52elif(zyan_slide[0]=='paa.png' and q_slide[0] == 'hikiwake.png' or zyan_slide[0]=='guu.png' and q_slide[0] == 'kati.png' or zyan_slide[0]=='tyoki.png' and q_slide[0] == 'make.png'): 53 zyan.append(2)

以上のコードは、うまく実行できるのですが、
以下の関数を他ファイルから呼び出してくると、

from classfy02 import input_data
OpenCV Error: Assertion failed (size.width>0 && size.height>0) in imshow, file /Users/travis/build/skvark/opencv-python/opencv/modules/highgui/src/window.cpp, line 325 Traceback (most recent call last): File "test.py", line 28, in <module> cv2.imshow('screen', img) cv2.error: /Users/travis/build/skvark/opencv-python/opencv/modules/highgui/src/window.cpp:325: error: (-215) size.width>0 && size.height>0 in function imshow

以上のエラーが出てしまいます。
原因はどこにあるのでしょうか。

よろしくお願い致します。

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

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

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

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

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

guest

回答2

0

classfy02.pyの内容が質問文に記載されていないため、憶測での回答になっていますが、
他のpyファイルで定義した関数や変数を呼び出したいと仮定して回答します。

前回も指摘しましたが、あまり上手く伝わっていないのですこし他のアプローチで回答します。
■前提知識
pythonはモジュールをimportした時にモジュール内のトップレベルソースを全部実行します。

aaa.py

Python

1# -*- coding: UTF-8 -* 2print(__name__) 3print('aaa.py caller') 4 5 6def calculation(n): 7 print('calculation') 8 return 2**n 9

bbb.py

Python

1# -*- coding: UTF-8 -* 2import aaa 3print(__name__) 4print('bbb.py caller') 5 6print(aaa.calculation(2)) 7

python bbb.py

Python

1#出力結果 2aaa 3aaa.py caller 4__main__ 5bbb.py caller 6calculation 74

importで呼び出されたかのかそうでないかはnameで判断できます。
よって、どちらで呼び出されたのかを意識してソースコードを記述する必要があります。

■モジュール分割するときのポイント
1,まず各ファイル(モジュール)で行う事を決めてください。
できるだけ単一の処理内容になっていることがふさわしいです。

2,画面の入力/表示(View)とデータ(Model)を分ける。
画面からの入力された内容に対して、if文で判断していますが
a,画面から入力した内容をデータをlistまたはdictに格納する。
b,引数で渡されたlist/dictに対して処理を行う。
この2つの関数に分けると処理の結合度が低くなります。

3,循環するimportは避ける。下記のようなimportです。
aaa.py

Python

1import bbb

bbb.py

Python

1import aaa

循環importを行いたい時はimportで行いたい処理を切り出し、新規にccc.pyを作成してimportしてくださいな。
aaa.py

Python

1import ccc

bbb.py

Python

1import ccc

5,ソースの構成は以下のような形にする。
質問文のコードだとこうなります。

Python

1# 1,組み込みライブラリのimport文 2import os 3import random 4from datetime import datetime 5from tkinter import ttk 6from tkinter import * 7# 2,pipでインストールした import文 8import cv2 9import pandas as pd 10import pyautogui 11#自作したライブラリのimport文 12#from classfy02 import input_data 13 14#1,2,3のこの順番でimportすることにより間違ったimportによる名前空間の汚染が防げる事が多いです。 15 16# 他のモジュールからimport時に公開したい処理 17# import時はmainメソッドは呼び出されないことに注意すること。 18# よってmainメソッドの内容に依存する処理は記述してはダメです。 19# 例)calculationを公開 20def calculation(n): 21 return 2**n 22# Python ファイル名.pyを実行時に行いたい処理 23def main(): 24 #以下に処理を記述 25 pyautogui.doubleClick(86, 94) 26 27 zyan_slide = ['paa.png', 'guu.png', 'tyoki.png'] 28 q_slide = ['kati.png', 'make.png', 'hikiwake.png'] 29 30 data_time = [] 31 zyan, q = [], [] 32 33 random.shuffle(zyan_slide) 34 random.shuffle(q_slide) 35 36 que_list, task_list = [], [] 37 38 # 注視画像 39 img = cv2.imread('cross.png') 40 cv2.namedWindow('screen', cv2.WINDOW_NORMAL) 41 cv2.setWindowProperty('screen', cv2.WND_PROP_FULLSCREEN, cv2.WINDOW_FULLSCREEN) 42 cv2.imshow('screen', img) 43 cv2.waitKey(1000) 44 45 time = datetime.now() 46 data_time.append(time) 47 48 # 問題提示 49 img = cv2.imread(q_slide[0]) 50 cv2.namedWindow('screen', cv2.WINDOW_NORMAL) 51 cv2.setWindowProperty('screen', cv2.WND_PROP_FULLSCREEN, cv2.WINDOW_FULLSCREEN) 52 cv2.imshow('screen', img) 53 cv2.waitKey(2000) 54 img = cv2.imread(zyan_slide[0]) 55 cv2.namedWindow('screen', cv2.WINDOW_NORMAL) 56 cv2.setWindowProperty('screen', cv2.WND_PROP_FULLSCREEN, cv2.WINDOW_FULLSCREEN) 57 cv2.imshow('screen', img) 58 cv2.waitKey(2000) 59 60 # グー:0、チョキ:1、パー:2 61 if (zyan_slide[0] == 'guu.png' and q_slide[0] == 'hikiwake.png' or zyan_slide[0] == 'tyoki.png' and q_slide[ 62 0] == 'kati.png' or zyan_slide[0] == 'paa.png' and q_slide[0] == 'make.png'): 63 zyan.append(0) 64 elif (zyan_slide[0] == 'tyoki.png' and q_slide[0] == 'hikiwake.png' or zyan_slide[0] == 'paa.png' and q_slide[ 65 0] == 'kati.png' or zyan_slide[0] == 'guu.png' and q_slide[0] == 'make.png'): 66 zyan.append(1) 67 elif (zyan_slide[0] == 'paa.png' and q_slide[0] == 'hikiwake.png' or zyan_slide[0] == 'guu.png' and q_slide[ 68 0] == 'kati.png' or zyan_slide[0] == 'tyoki.png' and q_slide[0] == 'make.png'): 69 zyan.append(2) 70 71if __name__ == '__main__': 72 main() 73

■余談
同じ処理を2回書いたらこれは関数化できるのか?どうかを一考してみてくださいな。

投稿2018/01/18 11:21

編集2018/01/18 11:35
umyu

総合スコア5846

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

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

gymgym

2018/01/19 02:26

丁寧にアドバイスいただきありがとうござます。 参考にコードを組んでいきたいと思います!
guest

0

ベストアンサー

カレントディレクトリが異なるためでしょう。
ご提示のエラーは、画像のオープンに失敗したときによく見るエラーです。

絶対パスで書けば解決するはずですが、移植性がなくなりますので...
サンプルとして、こんなコードを紹介してみます。

Python

1from pathlib import Path 2 3parent_path = Path(__file__).parent 4path = str( 5 (parent_path / 'myimg.jpg').resolve() 6) 7 8print(type(path), path)

どう適用すればいいかは、ちょっと考えてみてください。

ついでに

test.pyという名前は標準ライブラリのtestと被るので、避けてください。
Pythonでtest.pyを作るな!

あと、モジュールレベルにコードをべた書きするのはやめた方がいいです。
pythonで小さなツールを作る時のtips

投稿2018/01/18 06:31

編集2018/01/18 06:37
LouiS0616

総合スコア35660

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

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

gymgym

2018/01/19 02:25

回答ありがとうございます。 お手数ですが質問させていただきます。 カレントディレクトリが異なるという指摘を頂いきましたが、画像とコードはすべて同じディレクトリに入っています。それでは、まだ不十分であるということでしょうか。 よろしくお願い致します。
gymgym

2018/01/19 02:54

LouiS0616 さんのアドバイスを参考に簡単なコードで実行してみました。 from pathlib import Path import cv2 from classfy02 import input_data def main(): parent_path = Path(__file__).parent path = str( (parent_path / 'cross.png').resolve() ) img = cv2.imread(path) cv2.namedWindow('screen', cv2.WINDOW_NORMAL) cv2.setWindowProperty('screen', cv2.WND_PROP_FULLSCREEN, cv2.WINDOW_FULLSCREEN) cv2.imshow('screen', img) cv2.waitKey(1000) if __name__ == '__main__': main() やはり、これでもfrom classfy02 import input_dataがあることで以下のエラーが出ています。 OpenCV Error: Assertion failed (size.width>0 && size.height>0) in imshow, file /Users/travis/build/skvark/opencv-python/opencv/modules/highgui/src/window.cpp, line 325 Traceback (most recent call last): File "path.py", line 19, in <module> main() File "path.py", line 15, in main cv2.imshow('screen', img) cv2.error: /Users/travis/build/skvark/opencv-python/opencv/modules/highgui/src/window.cpp:325: error: (-215) size.width>0 && size.height>0 in function imshow from classfy02 import input_dataがなければうまく実行できます。 何度も申し訳ないのですがよろしくお願い致します。
LouiS0616

2018/01/19 06:46

> 画像とコードはすべて同じディレクトリに入っています。それでは、まだ不十分であるということでしょうか。 Pythonインタプリタを起動した際のカレントディレクトリに依ります。
LouiS0616

2018/01/19 06:48

pathをprintして、利用通りになっているか確認した方がいいですよ。 あと、エラーが発生しているのはもともとinput_data.py内じゃなかったんですか?
gymgym

2018/01/19 06:56

回答ありがとうございます。 >Pythonインタプリタを起動した際のカレントディレクトリに依ります 了解です!もう一度確認してみます。
gymgym

2018/01/19 06:57

> あと、エラーが発生しているのはもともとinput_data.py内じゃなかったんですか? input_data単体ではエラーは出ていません。 呼び出しを行うと画像が表示できないというエラーが出てしまいます。
LouiS0616

2018/01/19 07:13

『呼び出した際のカレントディレクトリによって、input_data内でエラーが発生している』のかと。 そういう意味で、『カレントディレクトリに依存しない』ようにする工夫はinput_data側に必要です。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問