n维的点分布
Points distribution in n-dimension
积分怎么分配才能像Fig.A
图B的matlab代码:
N = 30; % number of points
r = 0.5; % r = radius
d = 50; % dimension
C_point = 0; % center point
figure, clf
C = ones(1, d) * C_point;
C_rep = repmat( C,N,1);
X = randn(N,d);
s2 = sum(X.^2,2) ;
radius = r * (rand(N,1).^(1/d));
X = X.*repmat(radius./sqrt(s2),1,d) + C_rep;
%% Plot 2D
t = linspace(0, 2*pi, 100);
x = r*cos(t) + C(1);
y = r*sin(t) + C(2);
plot(x,y,'b')
hold on
plot(C(1),C(2),'b.', 'MarkerSize', 10) % center point
hold on
plot(X(:,1), X(:,2),'r.','markersize',10);
axis equal;rotate3d off; rotate3d on;drawnow;shg;
hold on
ax = axis;
我应该改成如图的样子。 A
OP 的代码计算在 d 维框中均匀分布的点,将这些点投影到 d 维球体上,然后对半径进行采样以将它们移动到 d 维球内。这是完美的,除了盒子内的点在投影到球体上时不会在该球体上形成均匀分布。相反,如果您找到分布在高斯分布中的随机点,则可以保证均匀的角度分布。
首先计算具有 d
维度高斯分布的点(我在这里对 OP 的代码进行了最小的更改):
N = 1000; % number of points
r = 0.5; % r = radius
d = 3; % dimension
C_point = 0; % center point
C = ones(1,d) * C_point;
C_rep = repmat(C,N,1);
X = randn(N,d);
请注意,我使用 randn
,而不是 rand
。 randn
创建高斯分布。
接下来我们对向量进行归一化,使点移动到球体上:
nX = sqrt(sum(X.^2,2));
X = X./repmat(nX,1,d);
这些点是均匀分布的,您可以通过 scatter3(X(:,1),X(:,2),X(:,3)); axis equal
并转动显示器来验证(2D 渲染并不公平)。这就是我上面设置d=3
和N=1000
的原因。我希望能够绘制点并看到很多点。
接下来我们计算到原点的随机距离,并根据维度对其进行校正:
radius = r * (rand(N,1).^(1/d));
X = X.*repmat(radius,1,d) + C_rep;
X
现在均匀分布在球中。同样,scatter3(X(:,1),X(:,2),X(:,3)); axis equal
显示了这一点。
但是,如果您设置 d=50
然后仅绘制数据的两个维度,您将看不到填满圆圈的数据。而且您也不会看到均匀分布。这是因为您将一个 50 维的球投影到 2 个维度上,这根本行不通。您要么必须相信数学,要么必须 切片 数据:
figure, hold on
t = linspace(0, 2*pi, 100);
x = r*cos(t) + C(1);
y = r*sin(t) + C(2);
plot(x,y,'b')
plot(C(1),C(2),'b.', 'MarkerSize', 10) % center point
axis equal
I = all(abs(X(:,3:d))<0.1,2);
plot(X(I,1), X(I,2),'r.','markersize',10);
I
那里的索引点在垂直于前两个显示的维度上靠近原点。同样,使用 d=50
时,您的点将很少,因此您需要将 N
设置得非常大!要查看与上述情况相同的点密度,对于您添加的每个维度,您需要将 N
乘以 10。因此对于 d=5
,您将有 N=1000*10*10=1e5
,对于d=50
你需要 N=1e50
。当然,这完全无法计算。
积分怎么分配才能像Fig.A
图B的matlab代码:
N = 30; % number of points
r = 0.5; % r = radius
d = 50; % dimension
C_point = 0; % center point
figure, clf
C = ones(1, d) * C_point;
C_rep = repmat( C,N,1);
X = randn(N,d);
s2 = sum(X.^2,2) ;
radius = r * (rand(N,1).^(1/d));
X = X.*repmat(radius./sqrt(s2),1,d) + C_rep;
%% Plot 2D
t = linspace(0, 2*pi, 100);
x = r*cos(t) + C(1);
y = r*sin(t) + C(2);
plot(x,y,'b')
hold on
plot(C(1),C(2),'b.', 'MarkerSize', 10) % center point
hold on
plot(X(:,1), X(:,2),'r.','markersize',10);
axis equal;rotate3d off; rotate3d on;drawnow;shg;
hold on
ax = axis;
我应该改成如图的样子。 A
OP 的代码计算在 d 维框中均匀分布的点,将这些点投影到 d 维球体上,然后对半径进行采样以将它们移动到 d 维球内。这是完美的,除了盒子内的点在投影到球体上时不会在该球体上形成均匀分布。相反,如果您找到分布在高斯分布中的随机点,则可以保证均匀的角度分布。
首先计算具有 d
维度高斯分布的点(我在这里对 OP 的代码进行了最小的更改):
N = 1000; % number of points
r = 0.5; % r = radius
d = 3; % dimension
C_point = 0; % center point
C = ones(1,d) * C_point;
C_rep = repmat(C,N,1);
X = randn(N,d);
请注意,我使用 randn
,而不是 rand
。 randn
创建高斯分布。
接下来我们对向量进行归一化,使点移动到球体上:
nX = sqrt(sum(X.^2,2));
X = X./repmat(nX,1,d);
这些点是均匀分布的,您可以通过 scatter3(X(:,1),X(:,2),X(:,3)); axis equal
并转动显示器来验证(2D 渲染并不公平)。这就是我上面设置d=3
和N=1000
的原因。我希望能够绘制点并看到很多点。
接下来我们计算到原点的随机距离,并根据维度对其进行校正:
radius = r * (rand(N,1).^(1/d));
X = X.*repmat(radius,1,d) + C_rep;
X
现在均匀分布在球中。同样,scatter3(X(:,1),X(:,2),X(:,3)); axis equal
显示了这一点。
但是,如果您设置 d=50
然后仅绘制数据的两个维度,您将看不到填满圆圈的数据。而且您也不会看到均匀分布。这是因为您将一个 50 维的球投影到 2 个维度上,这根本行不通。您要么必须相信数学,要么必须 切片 数据:
figure, hold on
t = linspace(0, 2*pi, 100);
x = r*cos(t) + C(1);
y = r*sin(t) + C(2);
plot(x,y,'b')
plot(C(1),C(2),'b.', 'MarkerSize', 10) % center point
axis equal
I = all(abs(X(:,3:d))<0.1,2);
plot(X(I,1), X(I,2),'r.','markersize',10);
I
那里的索引点在垂直于前两个显示的维度上靠近原点。同样,使用 d=50
时,您的点将很少,因此您需要将 N
设置得非常大!要查看与上述情况相同的点密度,对于您添加的每个维度,您需要将 N
乘以 10。因此对于 d=5
,您将有 N=1000*10*10=1e5
,对于d=50
你需要 N=1e50
。当然,这完全无法计算。