我正在用Python編寫我的第一個更大的項目,現在我想知道如何定義一個類方法,以便您可以在類的子類的類體中執行它。在Python中像DSL一樣的Ruby
首先給一些更多的上下文,鬆懈下來(我刪除了這個問題的一切非必要的)我如何做我想做的事情的例子Ruby: 如果我定義類Item
類似這樣的:
class Item
def initialize(data={})
@data = data
end
def self.define_field(name)
define_method("#{name}"){ instance_variable_get("@data")[name.to_s] }
define_method("#{name}=") do |value|
instance_variable_get("@data")[name.to_s] = value
end
end
end
我可以這樣使用它:
class MyItem < Item
define_field("name")
end
item = MyItem.new
item.name = "World"
puts "Hello #{item.name}!"
現在爲止我試圖實現的Python類似的東西,但我不愉快的結果,到目前爲止,我有:
class ItemField(object):
def __init__(self, name):
self.name = name
def __get__(self, item, owner=None):
return item.values[self.name]
def __set__(self, item, value):
item.values[self.name] = value
def __delete__(self, item):
del item.values[self.name]
class Item(object):
def __init__(self, data=None):
if data == None: data = {}
self.values = data
for field in type(self).fields:
self.values[field.name] = None
setattr(self, field.name, field)
@classmethod
def define_field(cls, name):
if not hasattr(cls, "fields"): cls.fields = []
cls.fields.append(ItemField(name, default))
現在我不知道如何使用子類的主體調用define_field
。這就是我想這是可能的:
class MyItem(Item):
define_field("name")
item = MyItem({"name": "World"})
puts "Hello {}!".format(item.name)
item.name = "reader"
puts "Hello {}!".format(item.name)
有this similar question但沒有一個答案是真正滿意,有人建議用__func__()
caling的功能,但我想我不能這樣做,因爲我不能從匿名內部獲得對類的引用(如果我對此有錯誤,請糾正我) 有人指出,使用模塊級函數來做這件事更好,我認爲這也是最簡單的方法,但是我這樣做的主要目的是使子類的實現變得乾淨,並且不得不加載該模塊函數也不會很好。 (另外我不得不在類體外進行函數調用,但我不知道但我認爲這很麻煩。)
所以基本上我認爲我的方法是錯誤的,因爲Python的設計不允許這種事情要做。用Python實現Ruby實例的最佳方式是什麼?
(如果沒有更好的辦法,我已經想過只是有在它返回的參數數組爲define_field
方法的子類的方法。)
對不起,我可能在我的問題中不夠清楚,但我真正的問題是我不知道如何調用子類中的'define_field'方法。我剛剛編輯了我的問題。 – evotopid 2015-01-09 19:42:19
噢,我不認爲這是可能的。不過,你可以在'__init__'裏面做。 – Kroltan 2015-01-09 20:03:14