0

This may appear like a very trivial question but I have just started learning python classes and objects. I have a code like below.

class Point(object):
    def __init__(self,x,y):
            self.x = float(x)
            self.y = float(y)
    def __str__(self):
            return '('+str(self.x)+','+str(self.y)+')'

def main():
p1 = Point(pt1,pt2)
p2 = Point(pt3,pt4)
p3 = Point(pt5,pt6)
p4 = Point(pt7,pt8)
parray = [p1,p2,p3,p4]
print " Points are", p1,p2,p3,p4
print "parray",parray

I m getting the below Output :

Points are (4.0,2.0) (4.0,8.0) (4.0,-1.0) (100.0,1.0) parray - intersection.Point object at 0x7ff09f00a550, intersection.Point object at 0x7ff09f00a410, intersection.Point object at 0x7ff09f00a590

My question is why are the addresses of objects assigned to array while I get the values while printing the objects? Can someone suggest a way to get the values returned by class in array in main function?

2 Answers2

0

Python containers, e.g. lists use an objects __repr__ method when printing their contents, not their __str__, Define __repr__ instead:

def __repr__(self):
    return '('+str(self.x)+','+str(self.y)+')'

If you want a more detailed explanation of __repr__ vs __str__ see here

blueenvelope
  • 699
  • 7
  • 15
0

When you print an object as an individual argument to a print statement in Python 2 or the print() function in Python 3, Python calls str on the object before printing it out.

When you put the object inside a container like a list and print the list, the list gets str called on it, but it in turn calls repr on each of the items it contains, rather than str. To understand why, look at the list [1, '2, 3', 4] and imagine what it would look like if the quotation marks were not included in the output when it was printed. The quotation marks are part of the '2, 3' string's repr.

So to make your class work the way you want, either rename your __str__ method to __repr__ (which will also work for str calls, since the default implementation of __str__ is to call __repr__), or add an additional __repr__ method. Sometimes it's useful to have a __repr__ that returns a less ambiguous string than __str__ does (for instance, it might name the class as well as the arguments). One common convention is to make __repr__ return a string that could be evaled to get an equivalent object again. For your class, that could look like:

def __repr__(self):
    return "{}({!r}, {!r})".format(type(self).__name__, self.x, self.y)

I'd also recommend using string formatting like this (or the older %s style if you prefer), rather than concatenating lots of strings together to build your result.

Blckknght
  • 100,903
  • 11
  • 120
  • 169