オブジェクト指向の例を説明します
クラス学校: school_name = ' OLDBOY ' デフ __init__ (自己、ニックネーム、ADDR): self.nickname = ニックネーム self.addr = ADDR self.classes = [] デフrelated_class(自己、CLASS_OBJ): #self.classes.append(班级名字) #self.classes.append(CLASS_NAME) self.classes.append(CLASS_OBJ) DEFの tell_class(セルフ): #変更 #のクラス名印刷 印刷(self.nickname.centerは(60、' = ' )) #クラスのコース情報印刷 用 CLASS_OBJをしてself.classes: class_obj.tell_course() ##A:学校 ##1、キャンパスの作成 school_obj1 =学校(' 少年魔法のキャンパスを'、' 上海' ) school_obj2 =学校(「オールドボーイズロイヤルパークキャンパス」、「北京」) # ##2、学校の提供クラスの #14フルタイム、フルタイムの上海キャンパスは15開く:#上海キャンパスが開かれた #1 school_obj1.related_class(「フルタイム14」) #1 school_obj1.related_class(「フルタイム15」) # ##北京キャンパス開設:フルタイム29 #school_obj2.related_class(「フルタイム29」) # ##3、各キャンパスオープンクラスビュー #school_obj1.tell_class() #1 )(school_obj2.tell_classを クラスクラス: デフ __init__ (自己、名): self.name = 名前 self.course = なし デフrelated_course(自己、course_obj): #self.course = COURSE_NAME self.course = course_obj DEF tell_course(自己): 印刷(' %sは'%self.name、端= " " ) self.course.tell_info() #印刷コースの詳細については、 #II:クラス #1、作成するクラス class_obj1クラス=(' フルタイム14 ' ) class_obj2 =クラス(" フルタイム15 " ) class_obj3 =クラス(" フルタイム29 " ) #2、クラスのためのプログラムアソシエイト #のclass_obj1.related_course( 'Pythonのフルスタックの開発') #1 class_obj2.related_course( 'Linuxの運用・保守') #1 class_obj3.related_course( 'Pythonのフルスタックの開発') #3、情報クラスのコースを参照 #class_obj1.tell_course() #class_obj2.tell_course() #のclass_obj3.tell_courseを() #4、学校の提供クラス #開かれた上海キャンパス:14フルタイムでは、上海キャンパスフルタイム15開く (class_obj1)school_obj1.related_classを school_obj1.related_class(class_obj2) #北京キャンパスが開か:フルタイム29 school_obj2.related_class(class_obj3) #school_obj1.tell_class() #のschool_obj2.tell_class() クラスコース: デフ __init__ (自己、名前、期間、価格): self.name = 名前 self.period = 期間 self.price = 価格 DEF (自己)tell_info: 印刷(' <プログラム名:%sのサイクル:%sの価格:%s>は'%(self.name、self.period、self.price)) #III:コース #1、作成したコース course_obj1もちろん、=(' Pythonのフルスタックの開発'、' 6mons '、20000 ) course_obj2 =コース(' Linuxの运维'、' 5mons '、18000 ) #2は、閲覧はもちろんの詳細 #course_obj1.tell_info() #1 )(course_obj2.tell_infoを #3、クラスのカリキュラムに関連するオブジェクトのための class_obj1.related_course(course_obj1) class_obj2.related_course(course_obj2) class_obj3.related_course(course_obj1) #class_obj1.tell_course() #class_obj2.tell_course() #のclass_obj3.tell_course() school_obj1.tell_class() school_obj2.tell_class()
パッケージ
オブジェクト指向プログラミングは、3つの特性を有している、最も重要な特徴は、パッケージカプセル化、継承、多態性です。パッケージは、データを参照し、機能が一体化され、非常に身近な音ではありません、はい、私たちは「統合」の前に言葉が実際に人気の引数のパッケージであると述べました。隠された、オープンインタフェース:また、オブジェクトまたはクラス属性へのパッケージのために、我々は、厳密に2つの段階で実現、それらへのアクセスを制御することができます
2つの隠し属性
Pythonは隠された属性が(プライベート配置された)道の初めに採用し、二重下線のクラスのメカニズムですが、すべてのプロパティのクラスの始まりは二重線は、クラス定義の位相検出自動文法に落ちているとき、実際にはこれは、操作の単なる変形であります「_ __クラス名属性名」の形式次のようになります。
class Foo:
__N=0 # 变形为_Foo__N def __init__(self): # 定义函数时,会检测函数语法,所以__开头的属性也会变形 self.__x=10 # 变形为self._Foo__x def __f1(self): # 变形为_Foo__f1 print('__f1 run') def f2(self): # 定义函数时,会检测函数语法,所以__开头的属性也会变形 self.__f1() #变形为self._Foo__f1() print(Foo.__N) # 报错AttributeError:类Foo没有属性__N obj = Foo() print(obbj.__x) # 报错AttributeError:对象obj没有属性__x
この変形の問題は、必要性の注意があること:
1クラスの外のプロパティに直接二重線の下落の始まりをアクセスしますが、あなたが名前を綴ることができ、クラスや属性の名前を知ることができない、:クラス名_ __プロパティを、あなたが訪問することができ、そのようFoo._A__Nようなので、このことそこには制限外部からのアクセスがなく、文法的な意味の単なる変形、厳密な意味で地面に作動します。
>>> Foo.__dict__
mappingproxy({..., '_Foo__N': 0, ...}) >>> obj.__dict__ {'_Foo__x': 10} >>> Foo._Foo__N 0 >>> obj._Foo__x 10 >>> obj._Foo__N 0
図2は、クラス属性内で直接このような二重型の内部相線特性低下の開始時にクラス定義に均一変形ので自己.__ F1()、のような減少し始めるアクセス二重線です。
>>> obj.f2() __f1 run
図3に示すように、変更後のクラス割り当ての定義は、クラス定義の段階でのみ発生したら、それを変形することはないであろう。
>>> Foo.__M=100 >>> Foo.__dict__ mappingproxy({..., '__M': 100,...}) >>> Foo.__M 100 >>> obj.__y=20 >>> obj.__dict__ {'__y': 20, '_Foo__x': 10} >>> obj.__y 20
3つのオープンインタフェース
カスタムプロパティを使用することで、それは隠蔽目的ではありません
3.1隠し属性データ
隠されたデータクラスは、インターフェイスクラスが間接外部操作データを許容提供する必要があり、インターフェースは厳密にデータの操作を制御するための追加ロジックに取り付けることができ、データに直接外部からの操作を制限します
>>> class Teacher:
... def __init__(self,name,age): #将名字和年纪都隐藏起来 ... self.__name=name ... self.__age=age ... def tell_info(self): #对外提供访问老师信息的接口 ... print('姓名:%s,年龄:%s' %(self.__name,self.__age)) ... def set_info(self,name,age): #对外提供设置老师信息的接口,并附加类型检查的逻辑 ... if not isinstance(name,str): ... raise TypeError('姓名必须是字符串类型') ... if not isinstance(age,int): ... raise TypeError('年龄必须是整型') ... self.__name=name ... self.__age=age ... >>> >>> t=Teacher('lili',18) >>> t.set_info(‘LiLi','19') # 年龄不为整型,抛出异常 Traceback (most recent call last): File "<stdin>", line 1, in <module> File "<stdin>", line 11, in set_info TypeError: 年龄必须是整型 >>> t.set_info('LiLi',19) # 名字为字符串类型,年龄为整形,可以正常设置 >>> t.tell_info() # 查看老师的信息 姓名:LiLi,年龄:19
3.2隠しプロパティ関数
目的は、このようななどのカード、認証、金額を入力し、小さなチケット印刷、引き出し、その他の多くの機能コンポーネントを備えていますATMの引き出し機能プログラムとして分離株の複雑さ、に、だけが必要なユーザーのためにあります引き出しは、この関数インタフェースを開発することができ、我々はすべての機能が隠されて休むことができます
>>> class ATM:
... def __card(self): #插卡 ... print('插卡') ... def __auth(self): #身份认证 ... print('用户认证') ... def __input(self): #输入金额 ... print('输入取款金额') ... def __print_bill(self): #打印小票 ... print('打印账单') ... def __take_money(self): #取钱 ... print('取款') ... def withdraw(self): #取款功能 ... self.__card() ... self.__auth() ... self.__input() ... self.__print_bill() ... self.__take_money() ... >>> obj=ATM() >>> obj.withdraw()
、およびクラス外でちょうどインターフェイスを取得するために、長いインターフェース名などとして、パラメータ変更せず、隠された属性とオープンインタフェースをまとめたもので、本質は明らかに内部と外部を区別することで、クラス内のコードの外部の発信者に影響を与えることなく、パッケージの中で何かを変更することができます設計者が内部実装コードを変更する方法に関係なく、ユーザーがコードを変更する必要がありません。長く同じ基本合意へのインタフェースとして、懸念のコード原因を修正するように、これは、協力のための良好な基礎を提供します。