我一直在学习Ruby中的元编程,并且发现它非常有用.我确信我可以在Python中做同样的事情.
例如:如何使用元编程以简洁和通用的方式重写此函数?
def foo(bar=None, baz=None, qux=None, haz=None):
txt = {}
if bar:
txt.update({'bar': bar})
if baz:
txt.update({'baz': baz})
if qux:
txt.update({'qux': qux})
if haz:
txt.update({'haz': haz})
return txt
Run Code Online (Sandbox Code Playgroud)
(这显然过于简化,实际上可能会根据各个键的值设置执行不同的任务)
python conditional dictionary exception-handling metaprogramming
我想在数组中使用字符串元素定义一个方法,例如:
ARRAY = ["name1", "name2"]
ARRAY.each do |k|
def k?
self.attribute == k
#or whatever else in here
end
end
Run Code Online (Sandbox Code Playgroud)
这样我就可以做到以下几点:
article.name1? #would return true of article.attribute == "name1"
Run Code Online (Sandbox Code Playgroud)
这样的事情可能吗?
显然这只是我可能做的一件事的一个简单例子,但我在这里真正得到的是如何根据字符串分配方法名称.
当我使用Array作为超类创建一个匿名类时,Array方法<<和[] =不会被继承.我的代码如下
class SubArray < Array
end
sa = SubArray.new
sa << "foo"
puts sa.inspect
sa_meta = Class.new(Array)
sa_meta << "foo"
puts sa_meta.inspect
Run Code Online (Sandbox Code Playgroud)
给出结果:
["foo"]
lib/so_example1.rb:9:in `<main>': undefined method `<<' for #<Class:0x6b10b8e4> (NoMethodError)
Run Code Online (Sandbox Code Playgroud)
我的红宝石版本是:
ruby 1.9.3p194 (2012-04-20 revision 35410) [i386-darwin11.4.2]
Run Code Online (Sandbox Code Playgroud)
如何用超类动态创建一个类?
在Ruby中,我可以写,
Dog = Class.new
Run Code Online (Sandbox Code Playgroud)
所以在这里,Dog是Object一个实例Class.
另外,我可以写
fido = Dog.new
Run Code Online (Sandbox Code Playgroud)
这只有在Doga时才有可能Class.
这是Dog一个Class还是一个Object?
我正在迭代一个哈希,如果哈希键匹配列名(由attr_accessible定义),那么我想更新该列.
def self.load_primer3_output(rawfile_hash)
primer3_output = Primer3Output.new
rawfile_hash.each do |key, value|
if primer3_output.class.accessible_attributes.include?(key)
primer3_output.send(key) = value
end
end
primer3_output.save
end
Run Code Online (Sandbox Code Playgroud)
我在发送时遇到语法错误:
** [out :: 192.241.193.126] /home/assay/apps/assay/releases/20130823054701/app/workers/primer3_query.rb:96: syntax error, unexpected '=', expecting keyword_end
** [out :: 192.241.193.126] (
** [out :: 192.241.193.126] SyntaxError
** [out :: 192.241.193.126] )
** [out :: 192.241.193.126]
** [out :: 192.241.193.126] primer3_output.send(key) = value
** [out :: 192.241.193.126]
** [out :: 192.241.193.126] ^
Run Code Online (Sandbox Code Playgroud)
编辑
顺便说一句,eval是有效的.我宁愿使用发送.
if primer3_output.class.accessible_attributes.include?(key)
#primer3_output.send(key) = value
eval("primer3_output.#{key} = value")
end
Run Code Online (Sandbox Code Playgroud) 事实证明,谷歌评论这个词真的很难.
是否可以在引号中表示"注释"表达式抽象语法树?
<@ //this gets ignored by the compiler and don't inject the quotation
@>
Run Code Online (Sandbox Code Playgroud)
如果没有,您能否建议一个解决方法来表示评论?
是否有可能获得name继承的匿名类,而不是提出"失败的A"?应该通过Class对象创建(没有评估或类似).
class A
def self.inherited(base)
raise 'fail A' unless base.name
end
end
B = Class.new(A)
# or
Object.const_set :B, Class.new(A)
Run Code Online (Sandbox Code Playgroud)
上面的代码不起作用,因为匿名类尚未初始化,因此无法将其设置为特定的常量.
我写了以下元编程模板:
template <unsigned int N, unsigned int P>
struct cutom_imagined
{
static unsigned int function(unsigned int r)
{
return (P + N + r) * cutom_imagined<N - 1>::function(r);
}
};
Run Code Online (Sandbox Code Playgroud)
P实际上就像一个常数.我应该如何编写上述示例的最后一次递归?我想它看起来应该与这个相似:
template <>
struct cutom_imagined<0, /* What should be here? */ >
{
static unsigned int function(unsigned int) { return 1; }
};
Run Code Online (Sandbox Code Playgroud)
但不知道怎么写它......
c++ recursion templates metaprogramming template-meta-programming
使用Python 2.7我需要将字典转换为类型化对象.
例如,如果我有这个词:
mapy = {'id': 1, 'name': 'bob'}
Run Code Online (Sandbox Code Playgroud)
给定前一个映射和类型名称('Person'在此示例中),我需要一些方法在运行时生成此类:
class Person:
def __init__(self):
self.id = id
self.name = name
Run Code Online (Sandbox Code Playgroud)
我应该考虑使用元编程技术,如果是这样,那么究竟是哪一个(装饰器,元类,......)?
请注意,我不仅需要将字典转换为对象; 我还需要将一些类型信息附加到结果对象.
请考虑以下代码:
module MyClass
def foo
"method"
end
end
Run Code Online (Sandbox Code Playgroud)
现在,我可以照常实例化此类的新类
@my_new_class = MyClass.new
Run Code Online (Sandbox Code Playgroud)
或者,我可以做一些元编程魔术
@my_new_class = Class.new { include MyClass }.send :new
Run Code Online (Sandbox Code Playgroud)
问题是两者之间有什么区别?
metaprogramming ×10
ruby ×6
dictionary ×2
python ×2
c++ ×1
class ×1
conditional ×1
f# ×1
recursion ×1
templates ×1