Python:staticmethod vs classmethod
2015-09-23 22:22
453 查看
Being educated under Java background, static method and class method are the same thing.
But not so in Python, there is subtle difference:
Say function a() is defined in Parent Class, while Sub Class extends Parent Class
If function a() has @staticmethod decorator, Sub.a() still refers to definition inside Parent Class. Whereas,
If function a() has @classmethod decorator, Sub.a() will points definition inside Sub Class.
Let’s talk about some definitions here:
@staticmethod function is nothing more than a function defined inside a class. It is callable without instantiating the class first. It’s definition is immutable via inheritance.
@classmethod function also callable without instantiating the class, but its definition follows Sub class, not Parent class, via inheritance. That’s because the first argument for @classmethod function must always be cls (class).
Let's assume an example of a class, dealing with date information (this is what will be our boilerplate to cook on):
This class obviously could be used to store information about certain dates (without timezone information; let's assume all dates are presented in UTC).
Here we have
Classmethod
We have some tasks that can be nicely done using
Let's assume that we want to create a lot of
So what we must do here is:
Parse a string to receive day, month and year as thee integer variables or a 3-item tuple consisting of that variable.
Instantiate
This will look like:
For this purpose, C++ has such feature as overloading, but Python lacks that feature- so here's when
Let's look more carefully at the above implementation, and review what advantages we have here:
We've implemented date string parsing in one place and it's reusable now.
Encapsulation works fine here (if you think that you could implement string parsing as a single function elsewher, this solution fits OOP paradigm far better).
Staticmethod
What about
Let's look at the next use case.
We have a date string that we want to validate somehow. This task is also logically bound to
Here is where
So, as we can see from usage of
Ref:
http://stackoverflow.com/questions/38238/what-are-class-methods-in-python-for
http://stackoverflow.com/questions/136097/what-is-the-difference-between-staticmethod-and-classmethod-in-python
http://stackoverflow.com/questions/12179271/python-classmethod-and-staticmethod-for-beginner
http://julien.danjou.info/blog/2013/guide-python-static-class-abstract-methods
But not so in Python, there is subtle difference:
Say function a() is defined in Parent Class, while Sub Class extends Parent Class
If function a() has @staticmethod decorator, Sub.a() still refers to definition inside Parent Class. Whereas,
If function a() has @classmethod decorator, Sub.a() will points definition inside Sub Class.
Let’s talk about some definitions here:
@staticmethod function is nothing more than a function defined inside a class. It is callable without instantiating the class first. It’s definition is immutable via inheritance.
@classmethod function also callable without instantiating the class, but its definition follows Sub class, not Parent class, via inheritance. That’s because the first argument for @classmethod function must always be cls (class).
Let's assume an example of a class, dealing with date information (this is what will be our boilerplate to cook on):
classDate(object): day =0 month =0 year =0 def __init__(self, day=0, month=0, year=0):self.day = day self.month = month self.year = year
This class obviously could be used to store information about certain dates (without timezone information; let's assume all dates are presented in UTC).
Here we have
__init__, a typical initializer of Python class instances, which receives arguments as a typical
instancemethod, having the first non-optional argument (
self) that holds reference to a newly created instance.
Classmethod
We have some tasks that can be nicely done using
classmethods.
Let's assume that we want to create a lot of
Dateclass instances having date information coming from outer source encoded as a string of next format ('dd-mm-yyyy'). We have to do that in different places of our source code in project.
So what we must do here is:
Parse a string to receive day, month and year as thee integer variables or a 3-item tuple consisting of that variable.
Instantiate
Dateby passing those values to initialization call.
This will look like:
day, month, year = map(int, string_date.split('-')) date1 =Date(day, month, year)
For this purpose, C++ has such feature as overloading, but Python lacks that feature- so here's when
classmethodapplies. Lets create another "constructor".
@classmethod def from_string(cls, date_as_string): day, month, year = map(int, date_as_string.split('-')) date1 = cls(day, month, year)return date1 date2 =Date.from_string('11-09-2012')
Let's look more carefully at the above implementation, and review what advantages we have here:
We've implemented date string parsing in one place and it's reusable now.
Encapsulation works fine here (if you think that you could implement string parsing as a single function elsewher, this solution fits OOP paradigm far better).
clsis an object that holds class itself, not an instance of the class. It's pretty cool because if we inherit our
Dateclass, all children will have
from_stringdefined also.
Staticmethod
What about
staticmethod? It's pretty similar to
classmethodbut doesn't take any obligatory parameters (like
classmethodor
instancemethoddoes).
Let's look at the next use case.
We have a date string that we want to validate somehow. This task is also logically bound to
Dateclass we've used so far, but still doesn't require instantiation of it.
Here is where
staticmethodcan be useful. Let's look at the next piece of code:
@staticmethod def is_date_valid(date_as_string): day, month, year = map(int, date_as_string.split('-'))try:assert0<= day <=31assert0<= month <=12assert0<= year <=3999exceptAssertionError:returnFalsereturnTrue
So, as we can see from usage of
staticmethod, we don't have any access to what the class is- it's basically just a function, called syntactically like a method, but without access to the object and it's internals (fields and another methods), while classmethod does.
Ref:
http://stackoverflow.com/questions/38238/what-are-class-methods-in-python-for
http://stackoverflow.com/questions/136097/what-is-the-difference-between-staticmethod-and-classmethod-in-python
http://stackoverflow.com/questions/12179271/python-classmethod-and-staticmethod-for-beginner
http://julien.danjou.info/blog/2013/guide-python-static-class-abstract-methods
相关文章推荐
- Python __setattr__()、__getattr__()、__delattr__() (十)
- Python中运用正则表达式抓取网页图片
- python--关于函数传递
- Python抓取新闻标题和链接
- 【Python之旅】第三篇(三):Python正则表达式
- 【Python之旅】第三篇(三):Python正则表达式
- Python自动单元测试框架
- python教程
- python 多线程问题
- python连接odbc
- Python函数参数中的星号*(关键字参数与非关键字参数)
- Python 学习 (二) Python中的循环
- python属性详解
- Python格式字符串
- 关于Python 资源学习
- Python 学习(5)---类的相关知识整理(续)
- Python爬虫框架Scrapy获得定向打击批量招聘信息
- Python-Django-实例sadmin学习
- Python之threading模块简单使用
- Python学习笔记