Wolfram mathematica 使用带纯函数的Evaluate和SetDelayed
我想通过将列表传递给某个函数来计算下面的f:Wolfram mathematica 使用带纯函数的Evaluate和SetDelayed,wolfram-mathematica,Wolfram Mathematica,我想通过将列表传递给某个函数来计算下面的f: f = {z[1] z[2], z[2]^2}; a = % /. {z[1]-> #1,z[2]-> #2}; F[Z_] := Evaluate[a] & @@ Z ; 所以现在如果我尝试F[{1,2}]我得到了{2,4}。但仔细观察,F将返回定义 F[Z_] := (Evaluate[a] &) @@ Z 这取决于a的值,因此如果我们设置a=3,然后计算F[{1,2}],我们得到3。我知道添加最后一个&会使评估
f = {z[1] z[2], z[2]^2};
a = % /. {z[1]-> #1,z[2]-> #2};
F[Z_] := Evaluate[a] & @@ Z ;
所以现在如果我尝试F[{1,2}]
我得到了{2,4}
。但仔细观察,F将返回定义
F[Z_] := (Evaluate[a] &) @@ Z
这取决于a
的值,因此如果我们设置a=3
,然后计算F[{1,2}]
,我们得到3
。我知道添加最后一个&
会使评估[a]
保持不变,但是什么是优雅的解决方法呢?本质上,我需要强制对Evaluate[a]
进行评估,主要是为了提高效率,因为a
实际上相当复杂
请有人帮忙,并考虑到f
必须包含一个数组[z,2]
,该数组由一些未知的计算给出。这么写
F[Z_] := {Z[[1]]Z[[2]],Z[[2]]^2}
这还不够,我需要从我们的f
自动生成这个
非常感谢您的贡献请考虑在下面的问题上问你的未来问题。 你的问题不太可能成为风滚草,很多专家都会看你的问题
您可以将
a
的值注入函数
和SetDelayed
的主体中,使用和:
With[{body = a},
F[Z_] := body & @@ Z
]
检查定义:
Definition[F]
您会注意到,由于嵌套的作用域构造,Z
已变成Z$
,但行为是相同的
你在评论中说:
如果z[i]
的值被更改,那么这种解决方法就会失败,这再次让我感到困扰
虽然在上述定义了F[Z_]
之后,这应该不是问题,但如果您希望保护对a
所做的替换,可以使用正式符号,而不是Z
。这些是用Esc$z
Esc输入的,例如,对于正式的z。形式符号具有受保护的属性,并专门存在以避免此类冲突
这在笔记本中看起来比在这里好得多:
f = {\[FormalZ][1] \[FormalZ][2], \[FormalZ][2]^2};
a = f /. {\[FormalZ][1] -> #1, \[FormalZ][2] -> #2};
另一种方法是在Hold
表达式中进行替换,并通过使用Unevaluated
,保护规则本身不被计算:
ClearAll[f, z, a, F, Z]
z[2] = "Fail!";
f = Hold[{z[1] z[2], z[2]^2}];
a = f /. Unevaluated[{z[1] -> #1, z[2] -> #2}] // ReleaseHold;
With[{body = a},
F[Z_] := body & @@ Z
]
Definition[F]
“自然”的方式似乎将一切都作为参数传递给F[z_,fa_,fa_](具有方便的定义)。有什么理由不这样做吗?你的意思是像F[Z,F][1]:=(F/{Z[1]->1,Z[2]->2})和@Z
?这是可行的,但我认为这是一个低效的解决方案,因为有些东西需要使用数万次。如果z[i]
的值被更改,那么这种解决方法就会失败,这再次让我感到困扰。谢谢你的评论。太好了,谢谢。我也适当地注意到了Mathematica的专用站点。我现在就实施!
ClearAll[f, z, a, F, Z]
z[2] = "Fail!";
f = Hold[{z[1] z[2], z[2]^2}];
a = f /. Unevaluated[{z[1] -> #1, z[2] -> #2}] // ReleaseHold;
With[{body = a},
F[Z_] := body & @@ Z
]
Definition[F]
F[Z$_] := ({#1 #2, #2^2} &) @@ Z$