尝试将 np.piecewise 用于多元函数时出现 ValueError
Getting ValueError when trying to use np.piecewise for multivariate function
我正在尝试使用 np.piecewise
定义多元分段函数,如下所示:
X = np.array([
[1, 2],
[3, 4],
[5, 6]
])
pw = np.piecewise(
X,
[
np.abs(X[:, 0] - X[:, 1]) < 1,
np.abs(X[:, 0] - X[:, 1]) >= 1
],
[
lambda X: 1 + 2 * X[:, 0] + 3 * X[:, 1],
lambda X: 1.5 + 2.5 * X[:, 0] + 3.5 * X[:, 1]
]
)
运行 此代码段出现以下错误:
ValueError: shape mismatch: value array of shape (3,) could not be broadcast to indexing result of shape (3,2)
对于上下文,在此示例中,我试图表示一个映射 f: R^2 -> R,同时在 X
的每一行上对其进行评估。
有什么想法吗?我是否需要以不同方式定义最终参数以便索引正确广播?
如果您有来自 np.meshgrid
的两个数组,那么 IMO np.piecewise
更合适,这样 np.piecewise
可以将条件的维度与您的数组维度相匹配。
在您的例子中,要表示一个分段映射 $f:R^2 \to R$,输入的形状为 (n,2)
并逐行评估(每列代表一个变量),最简单的方法生成矢量化代码只需使用 np.select
:
def pw(X):
return np.select([np.abs(X[:,0] - X[:,1]) < 1, np.abs(X[:,0] - X[:,1]) >= 1],
[1 + 2 * X[:, 0] + 3 * X[:, 1], 1.5 + 2.5 * X[:, 0] + 3.5 * X[:, 1]])
和 pw(X)
得到你想要的答案。
通过使用结构化数组,我可以将二维公式转换为一维公式:
In [76]: X = np.array([(1,2),(3,4),(5,6)],'f,f')
In [77]: X
Out[77]: array([(1., 2.), (3., 4.), (5., 6.)], dtype=[('f0', '<f4'), ('f1', '<f4')])
In [78]: pw = np.piecewise(
...: X,
...: [
...: np.abs(X['f0'] - X['f1']) < 1,
...: np.abs(X['f0'] - X['f1']) >= 1
...: ],
...: [
...: lambda X: 1 + 2 * X['f0'] + 3 * X['f1'],
...: lambda X: 1.5 + 2.5 * X['f0'] + 3.5 * X['f1']
...: ]
...: )
In [79]: pw
Out[79]:
array([(11., 11.), (23., 23.), (35., 35.)],
dtype=[('f0', '<f4'), ('f1', '<f4')])
数字在 pw
中重复,因为 piecewise
return 是一个与 X
具有相同形状和 dtype 的数组,即使 lambdas
只有 return 个标量值。
我正在尝试使用 np.piecewise
定义多元分段函数,如下所示:
X = np.array([
[1, 2],
[3, 4],
[5, 6]
])
pw = np.piecewise(
X,
[
np.abs(X[:, 0] - X[:, 1]) < 1,
np.abs(X[:, 0] - X[:, 1]) >= 1
],
[
lambda X: 1 + 2 * X[:, 0] + 3 * X[:, 1],
lambda X: 1.5 + 2.5 * X[:, 0] + 3.5 * X[:, 1]
]
)
运行 此代码段出现以下错误:
ValueError: shape mismatch: value array of shape (3,) could not be broadcast to indexing result of shape (3,2)
对于上下文,在此示例中,我试图表示一个映射 f: R^2 -> R,同时在 X
的每一行上对其进行评估。
有什么想法吗?我是否需要以不同方式定义最终参数以便索引正确广播?
np.meshgrid
的两个数组,那么 IMO np.piecewise
更合适,这样 np.piecewise
可以将条件的维度与您的数组维度相匹配。
在您的例子中,要表示一个分段映射 $f:R^2 \to R$,输入的形状为 (n,2)
并逐行评估(每列代表一个变量),最简单的方法生成矢量化代码只需使用 np.select
:
def pw(X):
return np.select([np.abs(X[:,0] - X[:,1]) < 1, np.abs(X[:,0] - X[:,1]) >= 1],
[1 + 2 * X[:, 0] + 3 * X[:, 1], 1.5 + 2.5 * X[:, 0] + 3.5 * X[:, 1]])
和 pw(X)
得到你想要的答案。
通过使用结构化数组,我可以将二维公式转换为一维公式:
In [76]: X = np.array([(1,2),(3,4),(5,6)],'f,f')
In [77]: X
Out[77]: array([(1., 2.), (3., 4.), (5., 6.)], dtype=[('f0', '<f4'), ('f1', '<f4')])
In [78]: pw = np.piecewise(
...: X,
...: [
...: np.abs(X['f0'] - X['f1']) < 1,
...: np.abs(X['f0'] - X['f1']) >= 1
...: ],
...: [
...: lambda X: 1 + 2 * X['f0'] + 3 * X['f1'],
...: lambda X: 1.5 + 2.5 * X['f0'] + 3.5 * X['f1']
...: ]
...: )
In [79]: pw
Out[79]:
array([(11., 11.), (23., 23.), (35., 35.)],
dtype=[('f0', '<f4'), ('f1', '<f4')])
数字在 pw
中重复,因为 piecewise
return 是一个与 X
具有相同形状和 dtype 的数组,即使 lambdas
只有 return 个标量值。