有没有办法classmethod在C#中用Python 做什么?
也就是说,一个静态函数可以根据它使用的子类将Type对象作为(隐式)参数.
我想要的一个例子就是
class Base:
@classmethod
def get(cls, id):
print "Would instantiate a new %r with ID %d."%(cls, id)
class Puppy(Base):
pass
class Kitten(Base):
pass
p = Puppy.get(1)
k = Kitten.get(1)
Run Code Online (Sandbox Code Playgroud)
预期的产出是
Would instantiate a new <class __main__.Puppy at 0x403533ec> with ID 1.
Would instantiate a new <class __main__.Kitten at 0x4035341c> with ID 1.
Run Code Online (Sandbox Code Playgroud)
人们可以这样做:
class master:
@combomethod
def foo(param):
param.bar() # Param could be type as well as object
class slaveClass( master ):
@classmethod
def bar(cls):
print("This is class method")
slaveType = slaveClass
slaveType.foo()
class slaveInstance( master ):
def __init__(self, data):
self.data = data
def bar(self):
print("This is "+self.data+" method")
slaveType = slaveInstance("instance")
slaveType.foo()
Run Code Online (Sandbox Code Playgroud)
combomethod在" 创建同时是实例和类方法的方法 "中定义.
我的问题是,为什么这样,默认的第一个参数不能用作comboclass的参数?或者至少,为什么我不能将对象作为第一个参数传递给classmethod?我知道classmethod和instancemethods之间的区别,我知道装饰器,但我可能不明白如何进行内置@classmethod和self参数传递.有技术限制吗?或者,为什么还没有combomethod内置?
在Cocoa中,Apple经常使用以下范例:
[NSApplication sharedApplication]
[NSNotificationCenter defaultNotificationCenter]
[NSGraphicsContext currentContext]
[NSCalendar currentCalendar]
Run Code Online (Sandbox Code Playgroud)
等等.
他们也会偶尔使用的范例,我觉得是远有大量的代码时更清晰.
NSApp //which maps to [NSApplication sharedApplication]
Run Code Online (Sandbox Code Playgroud)
我希望能够在我自己的类中以及对其他类的扩展中使用这种全局变量.
MYClassInstance
NSDefaultNotificationCenter
NSCal /* or */ NSCurrentCalendar
Run Code Online (Sandbox Code Playgroud)
等等.
#define.简单地说#define NSCal [NSCalendar currentCalendar],但是就像我们现在所知道的那样,宏是邪恶的(或者他们说的),它似乎不是正确的Cocoa方式.
我能找到的唯一来源NSApp是APPKIT_EXTERN id NSApp;,这不是完全可重复使用的代码.除非我弄错了,所有这些代码确实定义NSApp为一个id世界.不幸的是没有帮助.
在我的搜索中,我设法找到了几个关于"全局常量"的引导,但是这样的事情:
extern NSString * const StringConstant;
Run Code Online (Sandbox Code Playgroud)
遗憾的是,它们仅限于编译时常量,并且无法映射到必要的类方法.
我希望能够推出自己NSApp风格的全局变量,这些变量映射到类方法[NSNotificationCenter defaultNotificationCenter].这可能吗?如果是这样,我应该怎么做呢?
我试图通过以下方式专门实现框架单例:
MySingletons.h
//...
extern id NSNotifCenter;
//...
Run Code Online (Sandbox Code Playgroud)
MySingletons.m
//...
+(void)initialize
{
NSNotifCenter = [NSNotificationCenter …Run Code Online (Sandbox Code Playgroud) 我正在学习Smalltalk的基础知识.有一个super关键字用于从子类方法中的超类调用方法:
Object subclass: # A
test
^1
A subclass: # B
test
^2
callSuper
^super test
Run Code Online (Sandbox Code Playgroud)
所以B new callSuper评估为1.
好.这很清楚.
所以现在,我正在为B类定义一堆类方法:
createNew1
^super new
createNew2
^self new
create
^self
createSuper
^super
Run Code Online (Sandbox Code Playgroud)
他们分别计算结果为a B,a B,B和一个错误(这说明我super是不是继承而是一种消息分派器的投).
为什么我会在关键字的情况下获得B课程实例super?a B和B对象有什么区别?我开始认为B对象是一个特殊的,单一的实例(就像static属性在其他语言中实现的)B,但仍然 - 我已经检查过它的类是一个B和子类是一个A.
super类方法中关键字的语义是什么?它与对象方法中的语义有何不同?通过调用self类方法可以获得的对象究竟是什么?
我想看到对象.__ new __()的源定义,并决定使用这种快速方式来访问该代码.为什么python给我一个TypeError (is not a type:method),当type()告诉我它是一个类型:方法?
(1)
>>> import inspect
>>> print inspect.getsource(object.__new__)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/local/Cellar/python/2.7.3/Frameworks/Python.framework/Versions/2.7/lib/python2.7/inspect.py", line 701, in getsource
lines, lnum = getsourcelines(object)
File "/usr/local/Cellar/python/2.7.3/Frameworks/Python.framework/Versions/2.7/lib/python2.7/inspect.py", line 690, in getsourcelines
lines, lnum = findsource(object)
File "/usr/local/Cellar/python/2.7.3/Frameworks/Python.framework/Versions/2.7/lib/python2.7/inspect.py", line 526, in findsource
file = getfile(object)
File "/usr/local/Cellar/python/2.7.3/Frameworks/Python.framework/Versions/2.7/lib/python2.7/inspect.py", line 420, in getfile
'function, traceback, frame, or code object'.format(object))
TypeError: <built-in method __new__ of type object at 0x10a2d9410> is …Run Code Online (Sandbox Code Playgroud) 我想覆盖该方法Selenium::WebDriver.for.这是我试过的:
module SeleniumWebDriverExtension
def self.for(browser, *args)
if browser != :phantomjs
super(browser, *args)
else
options = {
"phantomjs.cli.args" => ["--ssl-protocol=tlsv1"]
}
capabilities = Selenium::WebDriver::Remote::Capabilities.phantomjs(options)
super(browser, desired_capabilities: capabilities)
end
end
end
Selenium::WebDriver.prepend(SeleniumWebDriverExtension)
Run Code Online (Sandbox Code Playgroud)
但是我在Selenium::Webdriver.for(:phantomjs)调用时遇到错误.
NoMethodError: super: no superclass method `for' for Selenium::WebDriver::Driver:Class
Run Code Online (Sandbox Code Playgroud)
如何从重写方法调用原始方法?
我来自java背景,所以我在这里有点困惑。
考虑下面的代码片段:
class A():
def __init__(self, **kwargs):
self.obj_var = "I am obj var"
@classmethod
def class_method(cls):
print cls.obj_var # this line is in question here
cls.cls_obj = "I m class object"
return cls.cls_obj
Run Code Online (Sandbox Code Playgroud)
这会引发错误:
In [30]: a = A()
In [31]: a.obj_var
Out[31]: 'I am obj var'
In [32]: a.class_method()
---------------------------------------------------------------------------
AttributeError Traceback (most recent call last)
<ipython-input-32-3dcd9d512548> in <module>()
----> 1 a.class_method()
<ipython-input-29-9c0d341ad75f> in class_method(cls)
8 @classmethod
9 def class_method(cls):
---> 10 print cls.obj_var
11 cls.cls_obj = "I m …Run Code Online (Sandbox Code Playgroud) python instance-variables decorator class-method python-decorators
我正在编写一个通用类装饰器,它需要将装饰器应用于每个方法。我的第一个方法是这样的:
def class_decorator(cls):
for name, member in vars(cls).items():
# Ignore anything that is not a method
if not isinstance(member, (types.FunctionType, types.BuiltinFunctionType, classmethod, staticmethod)):
continue
setattr(cls, name, method_decorator(member))
return cls
Run Code Online (Sandbox Code Playgroud)
装饰器本身并不是很重要。看起来像这样:
def method_decorator(fn):
@functools.wraps(fn)
def wrapper(*args, **kwargs):
# do something
return fn(*args, **kwargs):
return wrapper
Run Code Online (Sandbox Code Playgroud)
一旦我测试了它,我遇到了一个问题,这不适用于静态或类方法,并且引发以下错误functools.wraps:
AttributeError: 'classmethod' object has no attribute '__module__'
Run Code Online (Sandbox Code Playgroud)
是的,classmethod或者staticmethods不是普通函数,甚至不是可调用函数。一般来说,如果你需要装饰一个classmethod,你首先应用你的装饰器,然后应用classmethod装饰器,但由于这是一个类装饰器,我无法影响装饰器的顺序。
对此有什么好的解决办法吗?
我想重写一个方法,并将不同的参数类型传递给它:
class Base {
public myMethod(myString: string): undefined {
return;
}
}
class Child extends Base {
public myMethod(myNumber: number): undefined {
return super.myMethod(String(myNumber));
}
}
Run Code Online (Sandbox Code Playgroud)
但这会产生打字错误:
类型'Child'的属性'myMethod'不能分配给基本类型'Base'的相同属性。类型'(myNumber:number)=> undefined'不能分配给类型'(myString:string)=> undefined'。参数“ myNumber”和“ myString”的类型不兼容。“字符串”类型不可分配给“数字”类型。
有没有一种方法而不会产生打字稿错误?
考虑以下元类/类定义:
class Meta(type):
"""A python metaclass."""
def greet_user(cls):
"""Print a friendly greeting identifying the class's name."""
print(f"Hello, I'm the class '{cls.__name__}'!")
class UsesMeta(metaclass=Meta):
"""A class that uses `Meta` as its metaclass."""
Run Code Online (Sandbox Code Playgroud)
我们知道,在元类中定义一个方法意味着它被类继承,并且可以被类使用。这意味着交互式控制台中的以下代码可以正常工作:
class Meta(type):
"""A python metaclass."""
def greet_user(cls):
"""Print a friendly greeting identifying the class's name."""
print(f"Hello, I'm the class '{cls.__name__}'!")
class UsesMeta(metaclass=Meta):
"""A class that uses `Meta` as its metaclass."""
Run Code Online (Sandbox Code Playgroud)
然而,这种方法的一个主要缺点是我们可能包含在方法定义中的任何文档都丢失了。如果我们help(UsesMeta)在交互式控制台中键入,我们会看到没有对方法的引用greet_user,更不用说我们在方法定义中放入的文档字符串了:
>>> UsesMeta.greet_user()
Hello, I'm the class 'UsesMeta'!
Run Code Online (Sandbox Code Playgroud)
现在当然,__doc__类的属性是 writable …
class-method ×10
python ×6
decorator ×3
inheritance ×2
c# ×1
cocoa ×1
docstring ×1
instance ×1
macros ×1
metaclass ×1
objective-c ×1
oop ×1
overriding ×1
prepend ×1
python-3.x ×1
ruby ×1
smalltalk ×1
typescript ×1