初学 Python ,学习到 Python 继承,觉得继承/多态在 Python 中基本是废的,麻烦大家帮我解惑, 非常感谢大家!下附疑惑代码

2017-02-04 16:27:57 +08:00
 palmers

代码如下:

class Student(object):
    def __init__(self,name,age,school):
        self.__name = name
        self.__age = age
        self.__school = school

    def toString(self):
        print('我是%s,我%s 岁了,在%s 上学.' %(self.__name,self.__age,self.__school))


class XiaoMing(Student):
    def __init__(self,name,age,school):
        self.__name = name
        self.__age = age
        self.__school = school

    ''' 覆写父类 toString()方法'''
    # def toString(self):
    #     print('我是%s,我%s 岁了,在%s 上学.' %(self.__name,self.__age,self.__school))
''' 接受 Student 任何子类对象'''
def fun(stu):
    stu.toString()

###测试
xm = XiaoMing('小明',25,'北大')
fun(xm) 

按照继承, XiaoMing继承自 Student, 且属性是一模一样的,则toString函数再写一遍是多余的, 道理讲,应该直接使用父类的 toString方法,就可以了, 但是我去掉XiaoMingtoString方法后,就找不到 自身实例的私有属性了, 因为 python 解释器将私有属性名改变了, 我就觉得在这里多态基本都是废的, 代码复用完全无效了,

顺便问下大家, 继承/多态 在python中还有那些有用的地方?

5919 次点击
所在节点    Python
42 条回复
guyskk
2017-02-04 19:15:37 +08:00
@palmers 单下划线也看做私有, Python 里面没有真正的私有,双下划线的属性一样有办法获取。
edimetia3d
2017-02-04 19:15:39 +08:00
@chris5641 正解.

我翻译一下:
派生类构造时没有调用基类的构造函数,导致基类成员没有被创建,直接输出自然报错.
palmers
2017-02-04 21:02:08 +08:00
@Allianzcortex 哈哈哈哈 是啊 java 我看 python 很多特性感觉都是 javascript 和 java 的结合体 那按照你说 意思 最根本的原因是我使用了双下划线导致属性私有不能继承,所以在 toString 方法中 self 指向不到动态传递的对象 xm 上,是这样的吧?但是我在父类中 toString 方法中打印了 self 确实是子类对象呢?
palmers
2017-02-04 21:03:01 +08:00
@guyskk 这个我了解, 但是 。。 可能我有强迫症 唉 算了 我以后就单下划线标识私有吧[_]
Allianzcortex
2017-02-04 21:07:40 +08:00
@palmers 呃..什么..Python 里的 self 就等价于 Java 里的 this ,唯一不同的是 Java 已经在每个方法里把实例绑定了,不需要手动声明 this ,而 Python 的设计理念要求程序员手动把类里面方法的第一个参数显式(explicit is better than implicit 这种)声明(不用 self 而用 foo/bar/abc/def 等其他变量来声明也可以,只是 self 是约定俗成的一种表现方法)。
palmers
2017-02-04 21:18:52 +08:00
@Allianzcortex 嗯嗯 这个我也测试过 是这样的 我个人觉得这是因为 python 动态语言特性导致的。 在 python 中,动态调用方法 其实是假象,只要方法签名相同,就能找到这个方法, 即使没有继承关系,就像 javasctipt 可以将一个函数随意的绑定到别的对象上。
PythonAnswer
2017-02-04 21:29:37 +08:00
要记住, python 的世界全部是 public 。忘掉 java 就能写出来简洁的东西了。不然写出来的东西只能长成 java 的样子。
junnplus
2017-02-04 21:35:01 +08:00
自己把其他语言的惯性思维带到学 python 上,怪 python 咯
workwonder
2017-02-04 21:50:21 +08:00
对我来说, JavaScript 才是略奇怪的。
palmers
2017-02-04 22:13:49 +08:00
@PythonAnswer 嗯嗯 记住了
palmers
2017-02-04 22:14:10 +08:00
@junnplus 是的 怪 python
palmers
2017-02-04 22:14:38 +08:00
@workwonder javascript 不仅仅是奇怪呀
mseasons
2017-02-04 22:35:52 +08:00
不用再写一遍函数,可以用父类的函数的。
weyou
2017-02-04 23:10:58 +08:00
如果你指的是传统语言的多态, python 是不支持的, python 支持的是鸭子类型,这可比多态强大多了。传统多态接受的对象必须是有相同的基类的,而 python 只要查找到对象支持某种相同的方法就可以调用。比如飞机对象有方法是“ fly()”,鸟也有相同的方法“ fly()”,你就可以写一个函数“ dofly(obj): obj.fly()”,同时接受飞机对象和鸟对象, 尽管它们不是同一个基类。
weyou
2017-02-04 23:16:18 +08:00
看了代码,感觉楼主就是想一对一翻译一下 Java 的代码,尽管 oop 思想是一致的,但要做到 pythonic 还是要系统的按部就班的学习一下 python
greatonce
2017-02-04 23:50:52 +08:00
__init__ 不是构造方法,这个是初始方法

__new__ 才是构造方法
Gem
2017-02-05 00:28:27 +08:00
看到 toString(),莫名其妙的想到了 Scala...
yinian1992
2017-02-05 03:40:54 +08:00
toString 的话可以重写 __str__ 。
20015jjw
2017-02-05 03:44:20 +08:00
建议你在骂语言辣鸡的之前 好好学一下
tairan2006
2017-02-05 07:01:49 +08:00
Python 的思路和 Java 完全不一样…另外楼主你的用法有问题

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/338062

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX