我在课堂上有一些关于staticmethods的问题.我将首先举一个例子.
例一:
class Static:
def __init__(self, first, last):
self.first = first
self.last = last
self.age = randint(0, 50)
def printName(self):
return self.first + self.last
@staticmethod
def printInfo():
return "Hello %s, your age is %s" % (self.first + self.last, self.age)
x = Static("Ephexeve", "M").printInfo()
Run Code Online (Sandbox Code Playgroud)
输出:
Traceback (most recent call last):
File "/home/ephexeve/Workspace/Tests/classestest.py", line 90, in <module>
x = Static("Ephexeve", "M").printInfo()
File "/home/ephexeve/Workspace/Tests/classestest.py", line 88, in printInfo
return "Hello %s, your age is %s" % (self.first + self.last, self.age)
NameError: …Run Code Online (Sandbox Code Playgroud) 我需要以一种方式处理类的两个对象,它将返回同一个类的第三个对象,并且我试图确定是否更好地将它作为一个独立的函数来接收两个对象并返回第三个或作为一种方法,它将采取另一个对象并返回第三个.
举个简单的例子.这会是:
from collections import namedtuple
class Point(namedtuple('Point', 'x y')):
__slots__ = ()
#Attached to class
def midpoint(self, otherpoint):
mx = (self.x + otherpoint.x) / 2.0
my = (self.y + otherpoint.y) / 2.0
return Point(mx, my)
a = Point(1.0, 2.0)
b = Point(2.0, 3.0)
print a.midpoint(b)
#Point(x=1.5, y=2.5)
Run Code Online (Sandbox Code Playgroud)
或这个:
from collections import namedtuple
class Point(namedtuple('Point', 'x y')):
__slots__ = ()
#not attached to class
#takes two point objects
def midpoint(p1, p2):
mx = (p1.x + p2.x) / 2.0
my = …Run Code Online (Sandbox Code Playgroud) Run Code Online (Sandbox Code Playgroud)class Circle: all_circles = [] # class variable @staticmethod def total_area(): for c in Circle.all_circles: # hardcode class name # do somethig @classmethod def total_area(cls): for c in cls.all_circles: # no hardcode class name # do something
我认为类方法更灵活,因为我们不对类进行硬编码
问题:
- 这是一个更好的问题吗?@staticmethod还是@classmethod?
- 哪些方案适合使用这些方法中的每一种?
问题就这么说了。我有一个抽象类,该抽象类在辅助函数中调用静态方法,并且我希望子类仅定义静态方法并与之一起运行。
也许我可以使用类似getattr的东西?我应该改用@classmethod吗?
我开发了这个简短的测试/示例代码,以更好地了解静态方法在Python中的工作方式。
class TestClass:
def __init__(self, size):
self.size = size
def instance(self):
print("regular instance method - with 'self'")
@staticmethod
def static():
print("static instance method - with @staticmethod")
def static_class():
print("static class method")
a = TestClass(1000)
a.instance()
a.static()
TestClass.static_class()
Run Code Online (Sandbox Code Playgroud)
该代码正常工作,不会返回任何错误。我的问题是:
我是否正确理解“自我”可以理解为类似于“将从实例中调用此方法”?
再说一遍,@ staticmethod背后的逻辑是什么?是否可以创建可以从实例调用的静态方法?不就是没有什么静态方法是什么?
为什么第二种方法比第三种方法更受青睐?(我假设装饰器存在,所以有一点要注意。)第三个选项似乎更简单,直接。
我读过了
由于staticmethod无法访问该类的实例,我不知道它和global function?
什么时候应该使用staticmethod?能举个好例子吗?
根据我读到的内容,类方法与静态方法大致相同,只有少数例外但具有提供类指针的优点.
因此,如果在类中定义了非实例方法,是否真的有理由在类方法上使用静态方法?
编辑:由于你们中的一些人很快将其视为与另一个问题的重复.这不是关于类和静态方法之间差异的问题.相反,在绝大多数情况下,当它们的功能重叠时,如何在两者之间做出决定是一个问题.
编辑#2:我问的原因是我正在重构其他人的一些现有代码.具体来说,有些子类与父级共享相同的模块,我打算将它们移动到单独的模块中.发生这种情况时,需要修复静态方法中对类外常量的引用.我可以通过以下方式之一完成此操作1.从父模块导入所有常量2.将所有常量移动到父类中,并将所有子静态方法更改为类方法3.添加"ParentClass".在每次引用常量之前
我个人想做#2,因为它避免了命名空间污染,这也是我问这个问题的原因.这主要是风格问题.希望这提供了足够的背景.
我在实现名为Parser的类中实现内部私有枚举类:“ LineCode”时遇到了麻烦。
LineCode:私有Enum类,它定义6种通用可能的代码行类型。我使用Enum实例化发送正则表达式模式,并在构造函数__init__中对其进行编译,然后将正则表达式匹配器作为类变量保存。
解析器:解析一种编程语言,与什么语言无关。解析器正在使用LineCode来标识行并相应地进行处理。
问题:我无法从静态方法访问__LineCode的枚举成员。我希望在__LineCode中有一个static方法“ matchLineCode(line)”,该方法从解析器接收一个字符串,然后按以下逻辑对Enum成员进行迭代:
这似乎并不简单,我无法访问枚举成员来执行此操作。
尝试:我尝试使用以下方法遍历枚举:
两者均失败,因为找不到__lineCode。
理想情况下: LineCode类必须是私有的,并且对于导入解析器的任何其他类都不可见。解析器必须使用LineCode类提供的静态方法来返回Enum。我愿意接受任何解决此问题或模仿此行为的解决方案。
我省略了一些不相关的Parser方法以提高可读性。码:
class Parser:
class __LineCode(Enum):
STATEMENT = ("^\s*(.*);\s*$")
CODE_BLOCK = ("^\s*(.*)\s*\{\s*$")
CODE_BLOCK_END = ("^\s*(.*)\s*\}\s*$")
COMMENT_LINE = ("^\s*//\s*(.*)$")
COMMENT_BLOCK = ("^\s*(?:/\*\*)\s*(.*)\s*$")
COMMENT_BLOCK_END = ("^\s*(.*)\s*(?:\*/)\s*$")
BLANK_LINE = ("^\s*$")
def __init__(self, pattern):
self.__matcher = re.compile(pattern)
@property
def matches(self, line):
return self.__matcher.match(line)
@property
def lastMatch(self):
try:
return self.__matcher.groups(1)
except:
return None
@staticmethod
def matchLineCode(line):
for lineType in **???**:
if lineType.matches(line): …Run Code Online (Sandbox Code Playgroud) 试图创建一个程序,当你点击按钮(生成代码)时,它从文件中提取一行数据并输出到
TypeError:generatecode()获取0个位置参数,但给出了1
from tkinter import *
class Window(Frame):
def __init__(self, master = None):
Frame.__init__(self, master)
self.master = master
self.init_window()
def init_window(self):
self.master.title("COD:WWII Codes")
self.pack(fill=BOTH, expand=1)
codeButton = Button(self, text = "Generate Code", command = self.generatecode)
codeButton.place(x=0, y=0)
def generatecode(self):
f = open("C:/Programs/codes.txt", "r")
t.insert(1.0. f.red())
root = Tk()
root.geometry("400x300")
app = Window(root)
root.mainloop()
Run Code Online (Sandbox Code Playgroud) python ×10
class-method ×3
oop ×2
api ×1
attributes ×1
decorator ×1
enums ×1
inheritance ×1
readability ×1
tkinter ×1