我想绘制在复数上定义的这个函数: if Floor(Re(z))%2==0, f(z)=z else f(z)=sin(z)
我尝试编写以下代码:
import cplot
import math
import numpy as np
def f(z):
if math.floor(np.real(z)[0])%2==0:
res =z
else:
res=np.sin(z)
return res
plt = cplot.plot(f, (-10, +10, 3000), (-10, 10, 3000),5)
plt.show()
但是没有用,程序完全忽略了sin函数的存在,我也不知道为什么
我以为这是因为我使用了
math.
和
np.
所以我测试的更简单函数
if Re(z)>=0, f(z) =z, else f(z)= sin(z)
import cplot
import numpy as np
def f(z):
if np.real(z)[0]>=0:
res =z
else:
res=np.sin(z)
return res
plt = cplot.plot(f, (-10, +10, 3000), (-10, 10, 3000),5)
plt.show()
这次
z
的存在被完全忽略了
我想也许问题来自
[0]
中
np.real(z)[0]
,但删除它会产生错误
ValueError:具有多个元素的数组的真值不明确。使用 a.any() 或 a.all()
我使用了它们,结果仍然相同,它完全忽略了
z
在我的第二个代码中,而且问题似乎出在
>
符号中,如果我将其更改为
<
它完全忽略
sin
我不知道如何解决这个问题我试图搜索与此相关的任何内容,但我发现没有任何有用的东西。
遇到的问题源于将 NumPy 数组与标量 Python
if
语句一起使用。NumPy 数组(比如你从
cplot.plot
函数传递给
f
的数组)可以有多个元素,而 Python 的
if
语句被设计用于评估单个布尔值。当你编写类似
if np.real(z) >= 0:
的内容时,你试图检查一个可能有多个元素的数组是否大于或等于零,这会导致错误“具有多个元素的数组的真值不明确”。
解决此问题的解决方案是使用 NumPy 的矢量化操作。NumPy 提供了一种称为
np.where
的函数,该函数允许你根据元素条件对数组执行基于元素的操作。
这是你的代码的更正版本:
import cplot
import numpy as np
def f(z):
return np.where(np.floor(np.real(z)) % 2 == 0, z, np.sin(z))
plt = cplot.plot(f, (-10, +10, 3000), (-10, 10, 3000), 5)
plt.show()
在这个代码中:
-
np.floor(np.real(z)) % 2 == 0
创建了一个布尔数组,该数组与输入数组z
的形状相同。如果z
中相应元素的实部的向下取整值为偶数,则此数组中的每个元素都为True
,否则为False
。 -
np.where
函数然后根据此条件数组选择z
或np.sin(z)
的值。如果条件数组中的元素为True
,它将从z
中选择相应的值,否则它将从np.sin(z)
中选择值。
通过这种方式,你无需使用任何显式
if
语句即可有效地将函数应用于整个输入数组
z
,从而避免出现错误并获得预期的行为。