Pertanyaan Menjelaskan variabel 'diri' python ke seorang pemula [duplikat]


Pertanyaan ini sudah memiliki jawaban di sini:

Saya sangat tidak tahu tentang jargon dan konsep OOP. Saya tahu secara konseptual objek apa itu, dan objek memiliki metode. Saya bahkan mengerti bahwa dalam python, kelas adalah objek! Itu keren, aku hanya tidak tahu apa artinya. Itu tidak mengklik dengan saya.

Saat ini saya mencoba memahami beberapa jawaban terperinci yang saya pikir akan menjelaskan pemahaman saya tentang python:

  1. Apa yang dilakukan kata kunci "menghasilkan" dengan Python?
  2. Apa itu metaclass dengan Python?

Pada jawaban pertama, penulis menggunakan kode berikut sebagai contoh:

>>> class Bank(): # let's create a bank, building ATMs
...    crisis = False
...    def create_atm(self) :
...        while not self.crisis :
...            yield "$100"

Saya tidak segera grok apa self menunjuk ke. Ini jelas merupakan gejala tidak memahami kelas, yang akan saya kerjakan di beberapa titik. Untuk memperjelas, dalam

>>> def func():
...   for i in range(3):
...     print i

aku mengerti itu i menunjuk ke suatu item dalam daftar range(3) yang, karena itu dalam fungsi, bukanlah global. Tetapi apa yang terjadi self "arahkan ke"?


30
2017-08-09 00:18


asal


Jawaban:


Saya akan mencoba menjernihkan beberapa kebingungan tentang kelas dan objek untuk Anda terlebih dahulu. Mari kita lihat blok kode ini:

>>> class Bank(): # let's create a bank, building ATMs
...    crisis = False
...    def create_atm(self) :
...        while not self.crisis :
...            yield "$100"

Komentarnya ada sedikit tipuan. Kode di atas tidak "membuat" bank. Ini mendefinisikan apa itu bank. Bank adalah sesuatu yang disebut properti crisis, dan fungsi create_atm. Itulah kata kode di atas.

Sekarang mari kita membuat bank:

>>> x = Bank()

Sana, x sekarang adalah bank. x memiliki properti crisis dan sebuah fungsi create_atm. Panggilan x.create_atm(); di python sama dengan memanggil Bank.create_atm(x);, jadi sekarang self mengacu pada x. Jika Anda menambahkan bank lain yang disebut y, menelepon y.create_atm() akan tahu untuk melihat ynilai krisis, bukan xkarena dalam fungsi itu self mengacu pada y.

self hanyalah konvensi penamaan, tetapi sangat baik untuk tetap menggunakannya. Masih layak untuk menunjukkan bahwa kode di atas setara dengan:

>>> class Bank(): # let's create a bank, building ATMs
...    crisis = False
...    def create_atm(thisbank) :
...        while not thisbank.crisis :
...            yield "$100"

85
2017-08-09 00:35



Ini dapat membantu Anda memikirkan tentang obj.method(arg1, arg2) sintaks permintaan sebagai gula sintaksis murni untuk panggilan method(obj, arg1, arg2) (kecuali itu method dicari melalui objtipe, dan bukan global).

Jika Anda melihatnya seperti itu, obj adalah argumen pertama untuk fungsi, yang secara tradisional diberi nama self dalam daftar parameter. (Anda dapat, sebenarnya, menamainya sesuatu yang lain, dan kode Anda akan bekerja dengan benar, tetapi coders Python lainnya akan mengerutkan kening pada Anda.)


18
2017-08-09 00:21



"diri"adalah objek contoh secara otomatis diteruskan ke metode instance kelas ketika dipanggil, untuk mengidentifikasi contoh yang memanggilnya. "diri"digunakan untuk mengakses atribut atau metode lain dari objek dari dalam metode. (metode pada dasarnya hanya fungsi yang termasuk dalam kelas)

"diri"Tidak perlu digunakan saat memanggil metode ketika Anda sudah memiliki instance yang tersedia.

Mengakses atribut "some_attribute" dari dalam sebuah metode:

class MyClass(object):
    some_attribute = "hello"

    def some_method(self, some_string):
        print self.some_attribute + " " + some_string

Mengakses atribut "some_attribute" dari instance yang ada:

>>> # create the instance
>>> inst = MyClass()
>>>
>>> # accessing the attribute
>>> inst.some_attribute
"hello"
>>> 
>>> # calling the instance's method
>>> inst.some_method("world") # In addition to "world", inst is *automatically* passed here as the first argument to "some_method".
hello world
>>> 

Berikut ini adalah kode kecil untuk menunjukkan bahwa diri adalah sama dengan contoh:

>>> class MyClass(object):
>>>     def whoami(self, inst):
>>>         print self is inst
>>>
>>> local_instance = MyClass()

>>> local_instance.whoami(local_instance)
True

Seperti yang disebutkan oleh orang lain, itu bernama "diri"dengan konvensi, tetapi bisa diberi nama apa pun.


12
2017-08-09 01:55



self mengacu pada contoh saat ini Bank. Saat Anda membuat yang baru Bank, dan telepon create_atm di atasnya, self akan secara implisit dilewatkan oleh python, dan akan merujuk ke bank yang Anda buat.


5
2017-08-09 00:23



Saya tidak segera grok apa self menunjuk ke. Ini jelas merupakan gejala tidak memahami kelas, yang akan saya kerjakan di beberapa titik.

self adalah argumen yang disampaikan ke fungsi. Dalam Python, argumen pertama ini secara implisit adalah objek di mana metode itu diaktifkan. Dengan kata lain:

class Bar(object):
    def someMethod(self):
        return self.field

bar = Bar()

bar.someMethod()
Bar.someMethod(bar)

Dua garis terakhir ini memiliki perilaku yang setara. (Kecuali kalau bar mengacu pada objek dari subkelas Bar -- kemudian someMethod() mungkin merujuk ke objek fungsi yang berbeda.)

Perhatikan bahwa Anda dapat menyebutkan argumen pertama "khusus" apa pun yang Anda inginkan - self hanyalah sebuah konvensi untuk metode.

aku mengerti itu i menunjuk ke suatu item dalam daftar range(3) yang, karena itu dalam fungsi, bukanlah global. Tetapi apa yang terjadi self "arahkan ke"?

Nama self tidak ada dalam konteks fungsi itu. Mencoba menggunakannya akan meningkatkan NameError.


Contoh transkrip:

>>> class Bar(object):
...     def someMethod(self):
...         return self.field
...
>>> bar = Bar()
>>> bar.field = "foo"
>>> bar.someMethod()
'foo'
>>> Bar.someMethod(bar)
'foo'
>>> def fn(i):
...     return self
...
>>> fn(0)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 2, in fn
NameError: global name 'self' is not defined

5
2017-08-09 00:23



Satu perspektif Rubyis (Ruby adalah bahasa pemrograman pertama saya, jadi saya mohon maaf atas abstraksi berlebihan dan berpotensi salah yang akan saya gunakan)

sejauh yang saya tahu, operator dot, misalnya:

os.path

seperti itu os dilewatkan path() sebagai variabel pertama "tidak terlihat"

Seolah-olah os.path BENAR-BENAR ini:

path(os)

Jika ada rantai daisy saya membayangkan bahwa ini:

os.path.filename

Akan menjadi seperti ini dalam kenyataan *:

filename(path(os))

Di sinilah bagian ofensif Jadi dengan variabel diri semua yang dilakukan adalah memungkinkan METODE KELAS (dari perspektif rubyist python 'metode instance' muncul menjadi metode kelas ...) untuk bertindak sebagai metode instan dengan mendapatkan sebuah contoh yang dilewatkan ke dalamnya sebagai variabel pertamanya ( melalui metode titik "licik" di atas) yang disebut self dengan perjanjian. Apakah diri bukan sebuah contoh

c = ClassName()
c.methodname

tetapi kelasnya sendiri:

ClassName.methodname

kelas akan diloloskan daripada instance.

OK, juga penting untuk diingat adalah bahwa __init__ Metode ini disebut "sihir" oleh beberapa orang. Jadi jangan khawatir tentang apa yang dilewatkan untuk menghasilkan instance baru. Jujur saja mungkin nil.


3
2017-07-02 16:16



Alasan "diri" ada (oleh konvensi) adalah bahwa ketika runtime Python melihat panggilan dari bentuk Object.Method (Param1, Param2), itu memanggil Metode dengan parameter (Object, Param1, Param2). Jadi jika Anda menyebut parameter pertama itu "diri", semua orang akan tahu apa yang Anda bicarakan.

Alasan Anda harus melakukan ini adalah subjek pertanyaan lain.

Sejauh metaclass, itu sesuatu yang jarang digunakan. Anda mungkin ingin melihat: http://python-history.blogspot.com/2009/04/metaclasses-and-extension-classes-aka.html, penulis asli dan Dictator Benevolent Saat Ini untuk Kehidupan Python menjelaskan apa ini, dan bagaimana hal itu terjadi. Dia juga memiliki artikel yang bagus tentang beberapa kemungkinan penggunaan, tetapi kebanyakan orang tidak pernah langsung menggunakannya sama sekali.


2
2017-08-09 00:30



selfmengacu pada sebuah instance dari kelas.


1
2017-08-09 00:21