文章目录
人工势场法的基本思想是在障碍物周围构建障碍物斥力势场,在目标点周围构建引力势场,类似于物理学中的电磁场
被控对象在这两种势场组成的复合场中受到斥力作用和引力作用,斥力和引力的合力指引着被控对象的运动,搜索无碰的避障路径。
更直观而言, 势场法是将障碍物比作是平原上具有高势能值的山峰, 而目标点则是具有低势能值的低谷。
引力势场主要与汽车和目标点间的距离有关, 距离越大, 汽车所受的势能值就越大; 距离越小, 汽车所受的势能值则越小, 所以引力势场的函数为:
U
a
t
t
(
q
)
=
1
2
η
ρ
2
(
q
,
q
g
)
(1)
\tag{1} U_{a t t}(q)=\frac{1}{2} \eta \rho^{2}\left(q, q_{g}\right)
Uatt(q)=21ηρ2(q,qg)(1)
其中
η
\eta
η 为正比例增益系数,
ρ
(
q
,
q
g
)
\rho\left(q, q_{g}\right)
ρ(q,qg) 为一个矢量, 表示汽车的位置
q
q
q 和目标点位置
q
g
q_{g}
qg 之间的欧式距离
∣
q
−
q
g
∣
\left|q-q_{g}\right|
∣q−qg∣, 矢量方向是从汽车的位置指向目标点位置。
相应的引力
F
att
(
q
)
F_{\text {att }}(q)
Fatt (q) 为引力场的负梯度,代表引力势场函数
U
a
t
t
(
q
)
U_{att}(q)
Uatt(q)的变化最快方向。
F
a
t
t
(
q
)
=
−
∇
U
a
t
t
(
q
)
=
−
η
ρ
(
q
,
q
g
)
(2)
\tag{2} F_{a t t}(q)=-\nabla U_{a t t}(q)=-\eta \rho\left(q, q_{g}\right)
Fatt(q)=−∇Uatt(q)=−ηρ(q,qg)(2)
决定障碍物斥力势场的因素是汽车与障碍物间的距离, 当汽车未进入障碍物的影响范围时, 其受到的势能值为零; 在汽车进入障碍物的影响范围后, 两者之间的距离越大, 汽车受到的势能值就越小, 距离越小, 汽车受到的势能值就越大。
斥力势场的势场函数为:
U
r
e
q
(
q
)
=
{
1
2
k
(
1
ρ
(
q
,
q
0
)
−
1
ρ
0
)
2
,
0
≤
ρ
(
q
,
q
0
)
≤
ρ
0
0
,
ρ
(
q
,
q
0
)
≥
ρ
0
(3)
\tag{3} U_{r e q}(q)=\left\{\begin{array}{lc} \frac{1}{2} k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right)^{2} ,& 0 \leq \rho\left(q, q_{0}\right) \leq \rho_{0} \\ 0 ,& \rho\left(q, q_{0}\right) \geq \rho_{0} \end{array}\right.
Ureq(q)={21k(ρ(q,q0)1−ρ01)2,0,0≤ρ(q,q0)≤ρ0ρ(q,q0)≥ρ0(3)
其中 k k k 为正比例系数, ρ ( q , q 0 ) \rho\left(q, q_{0}\right) ρ(q,q0) 为一矢量, 方向为从障碍物指向汽车, 大小为汽车与障碍物间的欧式距离 ∣ q − q 0 ∣ , ρ 0 \left|q-q_{0}\right|, \rho_{0} ∣q−q0∣,ρ0 为一常数, 表示障碍物对汽车产生作用的最大影响范围。
由公式(3)可知,斥力势场不同于引力势场,智能汽车不总是受到障碍对它的斥力作用。当汽车与障碍物之间的相对距离超过 ρ 0 \rho_{0} ρ0时,就判定此障碍对汽车不再有影响作用。当汽车进入障碍物的影响范围之后,即汽车与障碍的相对距离小于 ρ 0 \rho_{0} ρ0时,汽车开始受到障碍物的斥力影响。汽车与障碍物的相对距离越小,斥力影响越大,自身势能升高。汽车与障碍物的相对距离越大,斥力影响越小,自身势能降低。
相应的斥力为斥力势场的负梯度作用力:
F
r
e
q
(
q
)
=
{
k
(
1
ρ
(
q
,
q
0
)
−
1
ρ
0
)
1
ρ
2
(
q
,
q
0
)
,
0
≤
ρ
(
q
,
q
0
)
≤
ρ
0
0
,
ρ
(
q
,
q
0
)
≥
ρ
0
(4)
\tag{4} F_{r e q}(q)= \begin{cases}k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right) \frac{1}{\rho^{2}\left(q, q_{0}\right)},& 0 \leq \rho\left(q, q_{0}\right) \leq \rho_{0} \\ 0 ,& \rho\left(q, q_{0}\right) \geq \rho_{0}\end{cases}
Freq(q)={k(ρ(q,q0)1−ρ01)ρ2(q,q0)1,0,0≤ρ(q,q0)≤ρ0ρ(q,q0)≥ρ0(4)
根据上述定义的引力场函数和斥力场函数,可以得到整个运行空间的复合场,机器人的合力势场大小为机器人所受的斥力势场和引力势场之和,故合力势场总函数为:
U
(
q
)
=
U
a
t
t
(
q
)
+
U
r
e
q
(
q
)
(5)
\tag{5} U(q)=U_{att}(q)+U_{req}(q)
U(q)=Uatt(q)+Ureq(q)(5)
所受合力为
F
(
q
)
=
−
∇
U
(
q
)
=
F
a
t
t
(
q
)
+
F
r
e
q
(
q
)
(6)
\tag{6} F(q) =-\nabla U(q)= F_{a t t}(q)+F_{r e q}(q)
F(q)=−∇U(q)=Fatt(q)+Freq(q)(6)
合力的方向决定汽车的行驶朝向,合力的大小决定汽车的行驶加速度。
不妨设车辆位置为 ( x , y ) (x, y) (x,y),障碍物位置为 ( x g , y g ) (x_g, y_g) (xg,yg)。
根据公式(1),引力势场函数为
U
a
t
t
(
q
)
=
1
2
η
ρ
2
(
q
,
q
g
)
⇒
U
a
t
t
(
x
,
y
)
=
1
2
η
[
(
x
−
x
g
)
2
+
(
y
−
y
g
)
2
]
(7)
\tag{7} U_{a t t}(q)=\frac{1}{2} \eta \rho^{2}\left(q, q_{g}\right) \Rightarrow U_{a t t}(x, y)=\frac{1}{2} \eta\left[\left(x-x_{g}\right)^{2}+\left(y-y_{g}\right)^{2}\right]
Uatt(q)=21ηρ2(q,qg)⇒Uatt(x,y)=21η[(x−xg)2+(y−yg)2](7)
故引力势场的负梯度有
−
grad
a
t
t
(
x
,
y
)
=
−
∇
U
a
t
t
(
x
,
y
)
=
−
U
a
t
t
,
x
′
(
x
,
y
)
i
⃗
−
U
a
t
t
,
y
′
(
x
,
y
)
j
⃗
=
−
η
(
x
−
x
g
)
i
⃗
−
η
(
y
−
y
g
)
j
⃗
=
η
[
(
x
g
−
x
)
i
⃗
+
(
y
g
−
y
)
j
⃗
]
⇒
引
力
大
小
=
η
(
x
−
x
g
)
2
+
(
y
g
−
y
)
2
=
η
ρ
(
q
,
q
g
)
(8)
\tag{8} \begin{aligned} -\operatorname{grad}_{a t t}(x, y)&=-\nabla U_{a t t}(x, y) \\ &=-U_{a t t, x}^{\prime}(x, y) \vec{i}-U_{a t t, y}^{\prime}(x, y) \vec{j} \\ &=-\eta\left(x-x_{g}\right) \vec{i}-\eta\left(y-y_{g}\right) \vec{j} \\ &=\eta\left[\left(x_{g}-x\right) \vec{i}+\left(y_{g}-y\right) \vec{j}\right] \\ \Rightarrow 引力大小&=\eta \sqrt{\left(x-x_{g}\right)^{2}+\left(y_{g}-y\right)^{2}}=\eta \rho\left(q, q_{g}\right) \end{aligned}
−gradatt(x,y)⇒引力大小=−∇Uatt(x,y)=−Uatt,x′(x,y)i−Uatt,y′(x,y)j=−η(x−xg)i−η(y−yg)j=η[(xg−x)i+(yg−y)j]=η(x−xg)2+(yg−y)2=ηρ(q,qg)(8)
同理,斥力势场函数为
U
r
e
q
(
q
)
=
1
2
k
(
1
ρ
(
q
,
q
0
)
−
1
ρ
0
)
2
⇒
U
r
e
q
(
x
,
y
)
=
1
2
k
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
2
(9)
\tag{9} \begin{aligned} U_{r e q}(q)=\frac{1}{2} k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right)^{2} \Rightarrow U_{r e q}(x, y)=\frac{1}{2} k\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]^{2} \end{aligned}
Ureq(q)=21k(ρ(q,q0)1−ρ01)2⇒Ureq(x,y)=21k⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤2(9)
斥力势场的负梯度为
−
∇
U
r
e
q
(
x
,
y
)
=
−
U
r
e
q
,
x
′
(
x
,
y
)
i
⃗
−
U
r
e
q
,
y
′
(
x
,
y
)
j
⃗
(10)
\tag{10} -\nabla U_{r e q}(x, y)=-U_{r e q, x}^{\prime}(x, y) \vec{i}-U_{r e q, y}^{\prime}(x, y) \vec{j}
−∇Ureq(x,y)=−Ureq,x′(x,y)i−Ureq,y′(x,y)j(10)
将公式(10)各项分别展开:
−
U
r
e
q
,
x
′
(
x
,
y
)
i
⃗
=
−
k
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
′
i
⃗
=
−
k
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
{
−
1
2
[
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
]
−
3
2
⋅
[
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
]
′
}
i
⃗
=
k
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
{
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
[
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
]
−
1
2
(
x
−
x
0
)
}
i
⃗
=
k
(
1
ρ
(
q
,
q
0
)
−
1
ρ
0
)
⋅
1
ρ
2
(
q
,
q
0
)
⋅
1
ρ
(
q
,
q
0
)
⋅
(
x
−
x
0
)
i
⃗
(11-1)
\tag{11-1} \begin{aligned} -U_{r e q, x}^{\prime}(x, y) \vec{i} &=-k\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]' \vec{i}\\ &=-k\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]\left\{-\frac{1}{2}\left[\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}\right]^{-\frac{3}{2}} \cdot\left[\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}\right]'\right\} \vec{i}\\ &=k\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]\left\{\frac{1}{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}\left[\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}\right]^{-\frac{1}{2}}\left(x-x_{0}\right)\right\} \vec{i}\\ &=k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right) \cdot \frac{1}{\rho^{2}\left(q, q_{0}\right)} \cdot \frac{1}{\rho\left(q, q_{0}\right)} \cdot\left(x-x_{0}\right) \vec{i}\\ \end{aligned}
−Ureq,x′(x,y)i=−k⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤′i=−k⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤{−21[(x−x0)2+(y−y0)2]−23⋅[(x−x0)2+(y−y0)2]′}i=k⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤{(x−x0)2+(y−y0)21[(x−x0)2+(y−y0)2]−21(x−x0)}i=k(ρ(q,q0)1−ρ01)⋅ρ2(q,q0)1⋅ρ(q,q0)1⋅(x−x0)i(11-1)
−
U
r
e
q
,
y
′
(
x
,
y
)
i
⃗
=
−
k
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
′
j
⃗
=
−
k
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
{
−
1
2
[
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
]
−
3
2
⋅
[
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
]
′
}
j
⃗
=
k
[
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
−
1
ρ
0
]
{
1
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
[
(
x
−
x
0
)
2
+
(
y
−
y
0
)
2
]
−
1
2
(
y
−
y
0
)
}
j
⃗
=
k
(
1
ρ
(
q
,
q
0
)
−
1
ρ
0
)
⋅
1
ρ
2
(
q
,
q
0
)
⋅
1
ρ
(
q
,
q
0
)
⋅
(
y
−
y
0
)
j
⃗
(11-2)
\tag{11-2} \begin{aligned} -U_{r e q, y}^{\prime}(x, y) \vec{i} &=-k\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]' \vec{j}\\ &=-k\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]\left\{-\frac{1}{2}\left[\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}\right]^{-\frac{3}{2}} \cdot\left[\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}\right]'\right\} \vec{j}\\ &=k\left[\frac{1}{\sqrt{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}}-\frac{1}{\rho_{0}}\right]\left\{\frac{1}{\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}}\left[\left(x-x_{0}\right)^{2}+\left(y-y_{0}\right)^{2}\right]^{-\frac{1}{2}}\left(y-y_{0}\right)\right\} \vec{j}\\ &=k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right) \cdot \frac{1}{\rho^{2}\left(q, q_{0}\right)} \cdot \frac{1}{\rho\left(q, q_{0}\right)} \cdot\left(y-y_{0}\right) \vec{j}\\ \end{aligned}
−Ureq,y′(x,y)i=−k⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤′j=−k⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤{−21[(x−x0)2+(y−y0)2]−23⋅[(x−x0)2+(y−y0)2]′}j=k⎣⎡(x−x0)2+(y−y0)21−ρ01⎦⎤{(x−x0)2+(y−y0)21[(x−x0)2+(y−y0)2]−21(y−y0)}j=k(ρ(q,q0)1−ρ01)⋅ρ2(q,q0)1⋅ρ(q,q0)1⋅(y−y0)j(11-2)
化简后得斥力大小为
−
∇
U
r
e
q
(
x
,
y
)
=
k
(
1
ρ
(
q
,
q
0
)
−
1
ρ
0
)
⋅
1
ρ
2
(
q
,
q
0
)
(12)
\tag{12} \begin{aligned} -\nabla U_{r e q}(x, y)=k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right) \cdot \frac{1}{\rho^{2}\left(q, q_{0}\right)} \end{aligned}
−∇Ureq(x,y)=k(ρ(q,q0)1−ρ01)⋅ρ2(q,q0)1(12)
由于障碍物与目标点距离太近,当汽车到达目标点时,根据势场函数可知,目标点的引力降为零,而障碍物的斥力不为零,此时汽车虽到达目标点, 但在斥力场的作用下不能停下来,从而导致目标不可达的问题。
车辆在某个位置时,无法向前搜索避障路径。
出现局部最优主要有两种情况:
解决方案可参考资料2和资料3,这两篇论文均给出了不一样的解决方案,但思路几乎差不多。下面以参考资料2给出的方案进行简单叙述。
通过改进障碍物斥力势场函数来解决局部最优和目标不可达的问题;在传统人工势场法的障碍物斥力场模型中加入调节因子 ρ g n \rho_{g}^{n} ρgn, 使汽车只有到达目标点时, 斥力和引力才同时减小到零, 从而使局部最优和目标不可达的问题得到解决。
改进后的斥力场函数为:
U
req
(
q
)
=
{
1
2
k
(
1
ρ
(
q
,
q
0
)
−
1
ρ
0
)
2
ρ
g
n
,
0
≤
ρ
(
q
,
q
0
)
≤
ρ
0
0
,
ρ
(
q
,
q
0
)
>
ρ
0
(13)
\tag{13} U_{\text {req }}(q)= \begin{cases}\frac{1}{2} k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right)^{2} \rho_{g}^{n}, & 0 \leq \rho\left(q, q_{0}\right) \leq \rho_{0} \\ 0, & \rho\left(q, q_{0}\right) > \rho_{0}\end{cases}
Ureq (q)=⎩⎨⎧21k(ρ(q,q0)1−ρ01)2ρgn,0,0≤ρ(q,q0)≤ρ0ρ(q,q0)>ρ0(13)
ρ
g
n
\rho_{g}^{n}
ρgn 为汽车与目标点的距离,式中
n
n
n为可选的正常数。
{ F r e q = F r e q 1 + F r e q 2 F r e q 1 = k ( 1 ρ ( q , q 0 ) − 1 ρ 0 ) ρ g n ρ 2 ( q , q 0 ) F r e q 2 = n 2 k ( 1 ρ ( q , q 0 ) − 1 ρ 0 ) 2 ρ g n − 1 (14) \tag{14} \left\{\begin{array}{l} F_{req}=F_{req1 }+F_{req2 }\\ \\ F_{req1 }=k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right) \frac{\rho_{g}^{n}}{\rho^{2}\left(q, q_{0}\right)} \\ F_{req2 }=\frac{n}{2} k\left(\frac{1}{\rho\left(q, q_{0}\right)}-\frac{1}{\rho_{0}}\right)^{2} \rho_{g}^{n-1} \end{array}\right. ⎩⎪⎪⎪⎪⎨⎪⎪⎪⎪⎧Freq=Freq1+Freq2Freq1=k(ρ(q,q0)1−ρ01)ρ2(q,q0)ρgnFreq2=2nk(ρ(q,q0)1−ρ01)2ρgn−1(14)
F r e q 1 F_{req1 } Freq1的方向为障碍物指向车辆; F r e q 2 F_{req2} Freq2的方向为车辆指向目标点。
改进的斥力场函数中加入了汽车与目标点间的距离,这样使汽车在驶向目标的过程中,受到的引力和斥力同时在一定程度上减小,且只有在汽车到达目标点时,引力和斥力才同时减小为零,即目标点成为势能值的最小点,从而使局部最优和目标不可达的问题得到解决。
如图,假设每一条车道宽度为 d d d,有2条车道(故道路宽度为 2 d 2d 2d)。车辆宽度为 w w w,故车辆在每一条车道内允许调整的横向移动范围为 d − w d-w d−w。
通过建立道路边界斥力势场以限制汽车的行驶区域,并适当考虑车辆速度对斥力场的影响
F
req,edge
=
{
η
edge
⋅
v
⋅
e
(
−
d
2
−
y
)
,
−
d
+
w
/
2
<
y
≤
−
d
/
2
车道1
1
3
η
edge
⋅
y
2
,
−
d
/
2
<
y
≤
−
w
/
2
车道1
−
1
3
η
edge
⋅
y
2
,
w
/
2
<
y
≤
d
/
2
车道2
η
edge
⋅
v
⋅
e
(
y
−
d
2
)
,
d
/
2
<
y
≤
d
−
w
/
2
车道2
(15)
\tag{15} F_{\text {req,edge }}= \begin{cases}\eta_{\text {edge }} \cdot v \cdot e^{\left(\frac{-d}{2}-y\right)}, & -d+w / 2<y \leq -d / 2 \text{ \quad \quad车道1} \\ \frac{1}{3} \eta_{\text {edge }} \cdot y^{2}, & -d / 2<y\leq -w / 2 \text{ \quad \quad车道1} \\ -\frac{1}{3} \eta_{\text {edge }} \cdot y^{2}, & w / 2<y\leq d / 2 \text{ \quad \quad车道2} \\ \eta_{\text {edge }} \cdot v \cdot e^{\left(y-\frac{d}{2}\right)}, & d / 2<y\leq d-w / 2\text{ \quad \quad车道2}\end{cases}
Freq,edge =⎩⎪⎪⎪⎪⎨⎪⎪⎪⎪⎧ηedge ⋅v⋅e(2−d−y),31ηedge ⋅y2,−31ηedge ⋅y2,ηedge ⋅v⋅e(y−2d),−d+w/2<y≤−d/2 车道1−d/2<y≤−w/2 车道1w/2<y≤d/2 车道2d/2<y≤d−w/2 车道2(15)
式中 η edge \eta_{\text {edge }} ηedge 是常数, v v v为车辆速度, y y y为车辆横向坐标。.
下面简单实现改进后的人工势场法。
初始化参数设置
import numpy as np
import matplotlib.pyplot as plt
import copy
from celluloid import Camera # 保存动图时用,pip install celluloid
%matplotlib qt5
## 初始化车的参数
d = 3.5 #道路标准宽度
W = 1.8 # 汽车宽度
L = 4.7 # 车长
P0 = np.array([0, - d / 2, 1, 1]) #车辆起点位置,分别代表x,y,vx,vy
Pg = np.array([99, d / 2, 0, 0]) # 目标位置
# 障碍物位置
Pobs = np.array([
[15, 7 / 4, 0, 0],
[30, - 3 / 2, 0, 0],
[45, 3 / 2, 0, 0],
[60, - 3 / 4, 0, 0],
[80, 3/2, 0, 0]])
P = np.vstack((Pg,Pobs)) # 将目标位置和障碍物位置合放在一起
Eta_att = 5 # 引力的增益系数
Eta_rep_ob = 15 # 斥力的增益系数
Eta_rep_edge = 50 # 道路边界斥力的增益系数
d0 = 20 # 障碍影响的最大距离
num = P.shape[0] #障碍与目标总计个数
len_step = 0.5 # 步长
n=1
Num_iter = 300 # 最大循环迭代次数
数据存储变量定义
path = [] # 保存车走过的每个点的坐标
delta = np.zeros((num,2)) # 保存车辆当前位置与障碍物的方向向量,方向指向车辆;以及保存车辆当前位置与目标点的方向向量,方向指向目标点
dists = [] # 保存车辆当前位置与障碍物的距离以及车辆当前位置与目标点的距离
unite_vec = np.zeros((num,2)) # 保存车辆当前位置与障碍物的单位方向向量,方向指向车辆;以及保存车辆当前位置与目标点的单位方向向量,方向指向目标点
F_rep_ob = np.zeros((len(Pobs),2)) # 存储每一个障碍到车辆的斥力,带方向
v=np.linalg.norm(P0[2:4]) # 设车辆速度为常值
人工势场法核心代码
## ***************初始化结束,开始主体循环******************
Pi = P0[0:2] # 当前车辆位置
# count=0
for i in range(Num_iter):
if ((Pi[0] - Pg[0]) ** 2 + (Pi[1] - Pg[1]) ** 2) ** 0.5 < 1:
break
dists=[]
path.append(Pi)
# print(count)
# count+=1
#计算车辆当前位置与障碍物的单位方向向量
for j in range(len(Pobs)):
delta[j]=Pi[0:2] - Pobs[j, 0:2]
dists.append(np.linalg.norm(delta[j]))
unite_vec[j]=delta[j]/dists[j]
#计算车辆当前位置与目标的单位方向向量
delta[len(Pobs)]=Pg[0:2] - Pi[0:2]
dists.append(np.linalg.norm(delta[len(Pobs)]))
unite_vec[len(Pobs)] = delta[len(Pobs)]/dists[len(Pobs)]
## 计算引力
F_att = Eta_att*dists[len(Pobs)]*unite_vec[len(Pobs)]
## 计算斥力
# 在原斥力势场函数增加目标调节因子(即车辆至目标距离),以使车辆到达目标点后斥力也为0
for j in range(len(Pobs)):
if dists[j] >= d0:
F_rep_ob[j] = np.array([0, 0])
else:
# 障碍物的斥力1,方向由障碍物指向车辆
F_rep_ob1_abs = Eta_rep_ob * (1 / dists[j] - 1 / d0) * (dists[len(Pobs)])**n / dists[j] ** 2 # 斥力大小
F_rep_ob1 = F_rep_ob1_abs*unite_vec[j] # 斥力向量
# 障碍物的斥力2,方向由车辆指向目标点
F_rep_ob2_abs = n/2 * Eta_rep_ob * (1 / dists[j] - 1 / d0) **2 *(dists[len(Pobs)])**(n-1) # 斥力大小
F_rep_ob2 = F_rep_ob2_abs * unite_vec[len(Pobs)] # 斥力向量
# 改进后的障碍物合斥力计算
F_rep_ob[j] = F_rep_ob1 + F_rep_ob2
# 增加道路边界斥力势场,根据车辆当前位置,选择对应的斥力函数
if Pi[1] > - d + W / 2 and Pi[1] <= - d / 2:
F_rep_edge = [0, Eta_rep_edge * v * np.exp(-d / 2 - Pi[1])] # 下道路边界区域斥力势场,方向指向y轴正向
elif Pi[1] > - d / 2 and Pi[1] <= - W / 2:
F_rep_edge = np.array([0, 1 / 3 * Eta_rep_edge * Pi[1] ** 2])
elif Pi[1] > W / 2 and Pi[1] <= d / 2:
F_rep_edge = np.array([0, - 1 / 3 * Eta_rep_edge * Pi[1] ** 2])
elif Pi[1] > d / 2 and Pi[1] <= d - W / 2:
F_rep_edge = np.array([0, Eta_rep_edge * v * (np.exp(Pi[1] - d / 2))])
## 计算合力和方向
F_rep = np.sum(F_rep_ob, axis=0)+F_rep_edge
F_sum = F_att+F_rep
UnitVec_Fsum = 1 / np.linalg.norm(F_sum) * F_sum
#计算车的下一步位置
Pi = copy.deepcopy(Pi+ len_step * UnitVec_Fsum)
# Pi[0:2] = Pi[0:2] + len_step * UnitVec_Fsum
# print(Pi)
path.append(Pg[0:2]) # 最后把目标点也添加进路径中
path=np.array(path) # 转为numpy
画图
## 画图
fig=plt.figure(1)
# plt.ylim(-4, 4)
plt.axis([-10,100,-15,15])
camera = Camera(fig)
len_line = 100
# 画灰色路面图
GreyZone = np.array([[- 5, - d - 0.5], [- 5, d + 0.5],
[len_line, d + 0.5], [len_line, - d - 0.5]])
for i in range(len(path)):
plt.fill(GreyZone[:, 0], GreyZone[:, 1], 'gray')
plt.fill(np.array([P0[0], P0[0], P0[0] - L, P0[0] - L]), np.array([- d /
2 - W / 2, - d / 2 + W / 2, - d / 2 + W / 2, - d / 2 - W / 2]), 'b')
# 画分界线
plt.plot(np.array([- 5, len_line]), np.array([0, 0]), 'w--')
plt.plot(np.array([- 5, len_line]), np.array([d, d]), 'w')
plt.plot(np.array([- 5, len_line]), np.array([- d, - d]), 'w')
# 设置坐标轴显示范围
# plt.axis('equal')
# plt.gca().set_aspect('equal')
# 绘制路径
plt.plot(Pobs[:,0],Pobs[:,1], 'ro') #障碍物位置
plt.plot(Pg[0],Pg[1], 'gv') # 目标位置
plt.plot(P0[0],P0[1], 'bs') # 起点位置
# plt.cla()
plt.plot(path[0:i,0],path[0:i,1], 'k') # 路径点
plt.pause(0.001)
# camera.snap()
# animation = camera.animate()
# animation.save('trajectory.gif')
效果如下:
代码仓库请移步github
由于在自动驾驶中算法实现一般使用C++,所以我也使用C++实现了相关功能,代码结构相比python代码封装得更好一些,更加清晰,这边就不再做相关代码解释了。完整代码详见另一个github仓库。
关闭。这个问题是opinion-based.它目前不接受答案。想要改进这个问题?更新问题,以便editingthispost可以用事实和引用来回答它.关闭4年前。Improvethisquestion我想在固定时间创建一系列低音和高音调的哔哔声。例如:在150毫秒时发出高音调的蜂鸣声在151毫秒时发出低音调的蜂鸣声200毫秒时发出低音调的蜂鸣声250毫秒的高音调蜂鸣声有没有办法在Ruby或Python中做到这一点?我真的不在乎输出编码是什么(.wav、.mp3、.ogg等等),但我确实想创建一个输出文件。
我有一个用户工厂。我希望默认情况下确认用户。但是鉴于unconfirmed特征,我不希望它们被确认。虽然我有一个基于实现细节而不是抽象的工作实现,但我想知道如何正确地做到这一点。factory:userdoafter(:create)do|user,evaluator|#unwantedimplementationdetailshereunlessFactoryGirl.factories[:user].defined_traits.map(&:name).include?(:unconfirmed)user.confirm!endendtrait:unconfirmeddoenden
这个问题在这里已经有了答案:关闭10年前。PossibleDuplicate:Pythonconditionalassignmentoperator对于这样一个简单的问题表示歉意,但是谷歌搜索||=并不是很有帮助;)Python中是否有与Ruby和Perl中的||=语句等效的语句?例如:foo="hey"foo||="what"#assignfooifit'sundefined#fooisstill"hey"bar||="yeah"#baris"yeah"另外,类似这样的东西的通用术语是什么?条件分配是我的第一个猜测,但Wikipediapage跟我想的不太一样。
什么是ruby的rack或python的Java的wsgi?还有一个路由库。 最佳答案 来自Python标准PEP333:Bycontrast,althoughJavahasjustasmanywebapplicationframeworksavailable,Java's"servlet"APImakesitpossibleforapplicationswrittenwithanyJavawebapplicationframeworktoruninanywebserverthatsupportstheservletAPI.ht
目录一.加解密算法数字签名对称加密DES(DataEncryptionStandard)3DES(TripleDES)AES(AdvancedEncryptionStandard)RSA加密法DSA(DigitalSignatureAlgorithm)ECC(EllipticCurvesCryptography)非对称加密签名与加密过程非对称加密的应用对称加密与非对称加密的结合二.数字证书图解一.加解密算法加密简单而言就是通过一种算法将明文信息转换成密文信息,信息的的接收方能够通过密钥对密文信息进行解密获得明文信息的过程。根据加解密的密钥是否相同,算法可以分为对称加密、非对称加密、对称加密和非
华为OD机试题本篇题目:明明的随机数题目输入描述输出描述:示例1输入输出说明代码编写思路最近更新的博客华为od2023|什么是华为od,od薪资待遇,od机试题清单华为OD机试真题大全,用Python解华为机试题|机试宝典【华为OD机试】全流程解析+经验分享,题型分享,防作弊指南华为o
我想解析一个已经存在的.mid文件,改变它的乐器,例如从“acousticgrandpiano”到“violin”,然后将它保存回去或作为另一个.mid文件。根据我在文档中看到的内容,该乐器通过program_change或patch_change指令进行了更改,但我找不到任何在已经存在的MIDI文件中执行此操作的库.他们似乎都只支持从头开始创建的MIDI文件。 最佳答案 MIDIpackage会为您完成此操作,但具体方法取决于midi文件的原始内容。一个MIDI文件由一个或多个音轨组成,每个音轨是十六个channel中任何一个上的
C#实现简易绘图工具一.引言实验目的:通过制作窗体应用程序(C#画图软件),熟悉基本的窗体设计过程以及控件设计,事件处理等,熟悉使用C#的winform窗体进行绘图的基本步骤,对于面向对象编程有更加深刻的体会.Tutorial任务设计一个具有基本功能的画图软件**·包括简单的新建文件,保存,重新绘图等功能**·实现一些基本图形的绘制,包括铅笔和基本形状等,学习橡皮工具的创建**·设计一个合理舒适的UI界面**注明:你可能需要先了解一些关于winform窗体应用程序绘图的基本知识,以及关于GDI+类和结构的知识二.实验环境Windows系统下的visualstudio2017C#窗体应用程序三.
本文主要介绍在使用Selenium进行自动化测试或者任务时,对于使用了iframe的页面,如何定位iframe中的元素文章目录场景描述解决方案具体代码场景描述当我们在使用Selenium进行自动化测试的时候,可能会遇到一些界面或者窗体是使用HTML的iframe标签进行承载的。对于iframe中的标签,如果直接查找是无法找到的,会抛出没有找到元素的异常。比如近在咫尺的例子就是,CSDN的登录窗体就是使用的iframe,大家可以尝试通过F12开发者模式查看到的tag_name,class_name,id或者xpath来定位中的页面元素,会抛出NoSuchElementException异常。解决
如何使此根路径转到:“/dashboard”而不仅仅是http://example.com?root:to=>'dashboard#index',:constraints=>lambda{|req|!req.session[:user_id].blank?} 最佳答案 您可以通过以下方式实现:root:to=>redirect('/dashboard')match'/dashboard',:to=>"dashboard#index",:constraints=>lambda{|req|!req.session[:user_id].b