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

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

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

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

オブジェクト指向

オブジェクト指向プログラミング(Object-oriented programming;OOP)は「オブジェクト」を使用するプログラミングの概念です。オブジェクト指向プログラムは、カプセル化(情報隠蔽)とポリモーフィズム(多態性)で構成されています。

Q&A

解決済

2回答

6041閲覧

Python メソッド間の変数の呼び出しについて

退会済みユーザー

退会済みユーザー

総合スコア0

Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

オブジェクト指向

オブジェクト指向プログラミング(Object-oriented programming;OOP)は「オブジェクト」を使用するプログラミングの概念です。オブジェクト指向プログラムは、カプセル化(情報隠蔽)とポリモーフィズム(多態性)で構成されています。

0グッド

1クリップ

投稿2017/04/14 16:09

編集2017/04/14 16:25

Pythonを勉強しておりまして、現在は主にオブジェクト指向の考え方を学んでおります(オブジェクト指向はほとんど初学です)。これまでに書いたシンプルなプログラムをクラスとメソッドで書き換えているのですが、わからない点があるので教えてください。(関数を使ったほうが良いところもあるかもしれませんが、勉強のつもりで書き換えました)

##やってみたこと
名前が

Darth Luke Darth Lea Darth Lea Lea Luke Darth Lea ...

のように続いているファイルをnameslist.txtとして、この名前の数をカウントするプログラムを以下のように書いてみました。

手順は、「ファイルの読み込み」->「名前の重複がないリストを作成」-> 「そのリストをelementとして読み込んだファイルの名前をカウント」です。

ファイルの読み込みと、重複するリストの生成は別々の役割を担うので、クラスを分けました。

class Read_file: #ファイルの読み込み def __init__(self): self.file = [] def read_file(self): with open('nameslist.txt', 'r') as fi: name = fi.read() self.file = name.split("\n") return self.file class Undup_list: def __init__(self, list): self.list = list def undup_list(self): #名前の取り出し new_list = [] for x in self.list: # creating unduplicated name list if x not in new_list: new_list.append(x) return sorted(new_list) def count_element(self, element): #elementの数をカウント return self.list.count(element) if __name__=='__main__' name_in = [] name_list =[] name_count =[] file_in = Read_file() #インスタンス生成 name_in = file_in.read_file() name = Undup_list(name_in) #インスタンス生成 name_list = name.undup_list() for i in range(len(name_list)): #counting names name_count.append(name.count_element(name_list[i])) print(dict(zip(name_list, name_count))) #辞書に変換

質問内容

クラス Read_file で読み込んだリスト(self.file)を、クラス Undup_listで使うことは可能でしょうか? つまり、それぞれが関数として書かれているならば、関数の中で他の関数を呼び出すことは可能ですが、クラス間ではこれは可能なのでしょうか?

##その他
もしこのコードの中で、こういうふうに書き換えればもっと短くなるというところがあれば教えていただけるとうれしいです。

いずれの内容も、高度なオブジェクト指向の内容を含んでいても構いません。

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

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

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

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

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

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

guest

回答2

0

すみません、コメント欄と間違えました。

投稿2017/04/16 12:52

編集2017/04/16 12:54
copepoda

総合スコア324

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

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

退会済みユーザー

退会済みユーザー

2017/04/16 12:55

ご丁寧に答えていただきありがとうございます。何度も申し訳ありませんでした。 次回以降は分けて行なうようにします。今回はお手数おかけしました。
guest

0

ベストアンサー

クラス Read_file で読み込んだリスト(self.file)を、クラス Undup_listで使うことは可能でしょうか? つまり、それぞれが関数として書かれているならば、関数の中で他の関数を呼び出すことは可能ですが、クラス間ではこれは可能なのでしょうか?

Undup_listクラスの初期化(__init__)時に、Read_fileクラスのインスタンスを引数で受け取るようにしたらいいのではないでしょうか。

Python

1# Read_file クラスは変更なし 2 3class Undup_list: 4 def __init__(self, reader): # 変更 5 self.reader = reader # 変更 6 7 def undup_list(self): 8 new_list = [] 9 for x in self.reader.read_file(): # 変更(Read_file.read_file メソッド実行) 10 if x not in new_list: 11 new_list.append(x) 12 return sorted(new_list) 13 14 def count_element(self, element): 15 return self.reader.file.count(element) # 変更 16 17if __name__=='__main__' 18 name_in = [] 19 name_list =[] 20 name_count =[] 21 file_in = Read_file() 22 # name_in = file_in.read_file() # 削除 23 24 name = Undup_list(file_in) # 変更(Read_file クラスのインスタンスを指定) 25 name_list = name.undup_list() 26 27 for i in range(len(name_list)): 28 name_count.append(name.count_element(name_list[i])) 29 print(dict(zip(name_list, name_count)))

もしこのコードの中で、こういうふうに書き換えればもっと短くなるというところがあれば教えていただけるとうれしいです。

コードは短くなりませんが、以下の一般的なオブジェクト指向を踏まえて実装しましたので例示します。

・クラス名は名詞(例: 車)
・メンバ変数はオブジェクトの状態や特性を保持する(例: 車.色)
・メソッドはオブジェクトに対する操作(例: 車.走行)

Python

1class NameList(list): 2 """名前のリスト 3 4 NameList は組み込みの list のサブクラスです。 5 標準の list メソッドに加えてファイルから名前を読み込む load メソッドを実装しています。 6 """ 7 def __init__(self, path=None): 8 """名前のリストを初期化します。 9 10 Args: 11 path (str): ファイルから名前を読み込む場合にパスを指定します。 12 """ 13 super().__init__() 14 15 if path: 16 self.load(path) 17 18 def load(self, path): 19 """ファイルから名前を読み込んで末尾に追加します。 20 21 Args: 22 path (str): ファイルパスを指定します。 23 """ 24 with open(path, 'r') as fp: 25 self.extend(fp.read().splitlines()) 26 27 28class Counter(dict): 29 """要素をキーとして、カウンタを値として保存する辞書 30 31 Counter は dict のサブクラスです。 32 標準の dict メソッドのうち、update メソッドをオーバーライドします。 33 """ 34 def __init__(self, iterable=None): 35 """カウンタを初期化します。 36 37 Args: 38 iterable (collections.Iterable): 初期化時にカウントする対象がある場合に指定します。 39 """ 40 super().__init__() 41 42 if iterable: 43 self.update(iterable) 44 45 def __missing__(self, key): 46 # 要素が存在しない場合は 0 を返します。 47 return 0 48 49 def update(self, iterable): 50 """カウンタを更新します。 51 52 Args: 53 iterable (Counter or collections.Iterable): 54 カウント対象のイテラブルオブジェクトを指定します。 55 Counter オブジェクトの場合、カウンタを合算します。 56 collections.Iterable の場合、カウンタをインクリメントします。 57 """ 58 if isinstance(iterable, Counter): 59 for key, count in iterable.items(): 60 self[key] += count 61 else: 62 for item in iterable: 63 self[item] += 1 64 65 66if __name__=='__main__' 67 print(Counter(NameList('nameslist.txt')))

なお、同等のことを普通に実装するなら以下のようになると思います。

Python

1from collections import Counter 2 3if __name__ == '__main__': 4 with open('nameslist.txt', 'r') as fp: 5 lines = fp.read().splitlines() 6 7 print(dict(Counter(lines)))

投稿2017/04/14 20:50

copepoda

総合スコア324

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

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

退会済みユーザー

退会済みユーザー

2017/04/14 21:10 編集

本当に丁寧な回答をいただきありがとうございます。助かりました!頂いた後者のソースコードは、後日勉強用に使わせていただきます。
退会済みユーザー

退会済みユーザー

2017/04/14 21:50

何度も申し訳ありません。再度質問させてください。 最初に頂いたソースコードのUndup_listクラスで for x in self.reader.read_file(): と書き換えていただきましたが、これはどういう風に解釈したら良いのでしょうか?別クラスの変数self.readerを用いて、なぜread_file()メソッドが呼び出せるのかわかりません。 また、インスタンスを生成する前の変数self.readerはクラスのデータ(情報)を持っていると考えてよいのでしょうか?(私が勉強した限りでは、クラスを使ってインスタンスを生成してからメソッドを呼び出す方法が主でした.) お手数をおかけしますが、以上よろしくお願いします。
copepoda

2017/04/15 06:43 編集

①最後の if __name__ == '__main__': ブロックは以下のとおりです。 file_in = Read_file() name = Undup_list(file_in) 最初に、Read_file クラスのインスタンスである file_in オブジェクトを作成しています。 次に、Undup_list クラスのインスタンスである name オブジェクトを作成しています。 このとき、file_in オブジェクトを初期化引数として渡しています。 ②Undup_list クラスの初期化(__init__)メソッドは以下のとおりです。 class Undup_list: def __init__(self, reader): # 変更 self.reader = reader # 変更 Undup_list クラスは、インスタンスの初期化時に、引数 reader を受け取って、 メンバ変数 self.reader として保存しています。 上述①のとおり、引数 reader には、file_in オブジェクトが渡ってきます。 ③Undup_list クラスの undup_list メソッドは以下のとおりです。 def undup_list(self): new_list = [] for x in self.reader.read_file(): # 変更(Read_file.read_file メソッド実行) self.reader は、上述②のとおり、初期化引数 reader で受け取った file_in オブジェクトを 保持するメンバ変数です。 file_in オブジェクトは、Read_file クラスのインスタンスであるため、 self.reader.read_file メソッドが呼び出せることがわかると思います。
退会済みユーザー

退会済みユーザー

2017/04/16 12:35 編集

お忙しい中、丁寧なコメント本当にありがとうございます。とても勉強になります。 今回は、クラスRead_file()から生成されたインスタンスfile_inを引数として、Undup_listクラスからインスタンスnameを生成している(頂いたコメントの①)ので、Undup_listクラス内でRead_file()クラスのメンバ変数を使えることはよくわかりました。 本当にありがとうございました。:)
copepoda

2017/04/16 12:53

一般的に継承は、クラスが is-a 関係の場合に行います。 つまり、"サブクラスは、スーパークラスの一種である"場合です。 "ファイルリーダー(Read_file)は、重複なしリスト(Undup_list)の一種である"は 成立しないため、継承関係にはならないと思います。 新たな質問は、新しく質問を作成されると、 他の方からの回答も得られやすくなって良いと思います。
退会済みユーザー

退会済みユーザー

2017/04/16 12:55

ご丁寧に答えていただきありがとうございます。何度も申し訳ありませんでした。 次回以降は分けて行なうようにします。今回はお手数おかけしました。
copepoda

2017/04/16 13:08

すみません、タイミングが悪かったみたいですね。 また、コメントの返信に時間がかかってしまってすみません。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問