Próbuję się dowiedzieć, jak działają klasy w Pythonie i nowość w tym, mam następującą klasę zdefiniowaną jako „Animal”:

class Animal(object):
    def __init__(self, size, color, mood):
    # init: consists of statements that bind the parameters passed to init to the instance o f the class, when an instance
    # is created.
        self.size = size
        self.color = color
        self.mood = mood
        self.alive = True

    def feeling(self):
        # first method, methods are limited to the class, that is why their name does not need to be unique.
        return "The", self.color, str(self), " is feeling", self.mood, "."

    def colors(self, other):
        return "The", str(self), "is", self.color, "and the", str(other), "is", other.color, "."

Następnie tworzę wystąpienie obiektu Animal w następujący sposób:

hippo = Animal("large", "purple", 'amused')

Na koniec wywołuję metodę na moim obiekcie w następujący sposób:

print(hippo.feeling())

Oczekuję, że wynik będzie taki jak poniżej:

"The purple hippo is feeling amused."

Ale to, co otrzymam na wyjściu, jeśli wydrukuję ten sam argument, co powyżej, to:

('The', 'purple', '<__main__.Animal object at 0x7f43cc978160>', ' is feeling', 'amused', '.')

Czy ktoś może wyjaśnić, dlaczego wynik jest podobny do listy? także dlaczego str (self) zwróciło nazwę obiektu, a nie słowo hippo.

Oryginalny kod w samouczku został napisany w Pythonie 3.5, myślałem, że to mogło być przyczyną, ale wypróbowałem IDE online na https://www.jdoodle.com/python3-programming-online/ dla Pythona 3.5.1 i wynik był taki sam.

2
Amin Edalat 3 kwiecień 2020, 09:10

4 odpowiedzi

Najlepsza odpowiedź

Musisz podać nazwę zwierzęcia podczas inicjalizacji - klasa nie będzie znała nazwy zmiennej.

class Animal(object):
    def __init__(self, name, size, color, mood):
    # init: consists of statements that bind the parameters passed to init to the instance of the class, when an instance
    # is created. 

    # pass the name to the class
        self.name = name
        self.size = size
        self.color = color
        self.mood = mood
        self.alive = True

    def feeling(self):
    # first method, methods are limited to the class, that is why their name does not need to be unique.
        return str("The " + self.color + " " + self.name + " is feeling " + self.mood + ".")

    def colors(self, other):
        return str("The ", self.name, " is " + self.color + " and the " + other.name, " is ", other.color, ".")

Wyjście:

hippo = Animal("hippo", "large", "purple", 'amused')
print(hippo.feeling())
# The purple hippo is feeling amused.
4
Ch3steR 3 kwiecień 2020, 06:37

Twoja metoda używa przecinków do oddzielania argumentów. Użyj f-string i wypisz zamiast zwracać, jak na przykład:

print(f”The {self.size} {self.color} Animal is feeling {self.mood}.”)

Oczekujesz również, że self zwróci w jakiś sposób nazwę zmiennej. Zamiast tego przekaż typ zwierzęcia do funkcji w init .

0
Theo 3 kwiecień 2020, 06:14

Jak odpowiedział @ Ch3steR, możesz użyć __repr__ lub __str__. Obie służą do tego celu. przykład jest jak poniżej:

>>> class Test:
...     def __repr__(self):
...         return "Test()"
...     def __str__(self):
...         return "member of Test"
... 
>>> t = Test()
>>> t
Test()
>>> print(t)
member of Test
1
Ch3steR 3 kwiecień 2020, 06:26

Jest kilka rzeczy, którymi należy się tutaj zająć

  1. Wartość zwracana przez funkcję def feeling(self) jest krotką, za każdym razem, gdy wartości zwracane są oddzielane przecinkiem, funkcja zwraca krotkę składającą się ze wszystkich zwracanych wartości. Dlatego staramy się wydrukować, jak wygląda lista. Więc albo zwróć ciąg, albo zmodyfikuj sposób wypisywania wartości zwracanych z krotki.
  2. Chcesz uzyskać nazwę instancji obiektu klasy podczas drukowania. to znaczy hippo = Animal("large", "purple", 'amused') w tym celu oczekujesz, że str (self) zwróci nazwę instancji, co jest trochę nietrywialne. Najpierw zdefiniuj tę funkcję def __str__(self):, aby uzyskać pożądane wyjście za każdym razem, gdy używasz str(self). Po drugie, aby uzyskać nazwę zmiennej, albo podaj nazwę jako zmienną klasy w konstruktorze i użyj jej, co byłoby prostszym sposobem, albo możesz użyć pakietu python-varname, aby użyć funkcji varname(), aby to osiągnąć.
class Klass:
    def __init__(self):
        self.id = varname()


k = Klass()
# k.id == 'k'
1
wolfsgang 3 kwiecień 2020, 06:37