在这个问题中,我们的目标是优化反潜作战中的投弹策略,以最大化命中潜艇的概率。通过调整投弹阵列的间隔(a
和 b
),以及引爆深度(Z_trigger
),我们可以设计出最优的投弹策略。代码主要通过三种投弹策略来计算命中概率,并使用粒子群优化(PSO)算法对这些策略进行优化。以下是详细的解题思路:
1. 基础参数与潜艇定位
- 定位误差:潜艇的水平定位误差服从正态分布,设定为
sigma_x = 50
和sigma_y = 50
。这些参数用于生成潜艇的位置。 - 炸弹阵列:投弹区域是一个 3x3 的矩阵,每个单元格代表一个炸弹的投放位置。
# 创建一个3x3的炸弹位置阵列
def bomb_positions():
return np.array([[0, 0], [0, 1], [0, 2],
[1, 0], [1, 1], [1, 2],
[2, 0], [2, 1], [2, 2]])
2. 命中概率计算
- 计算未命中区域的概率:炸弹未命中潜艇时,该区域会被排除在外,从而更新后续炸弹的命中概率。
# 计算未命中区域的概率(在正态分布中排除掉的区域)
def calc_excluded_prob(x, y, sigma_x, sigma_y, radius):
prob_x = norm.cdf(x + radius, 0, sigma_x) - norm.cdf(x - radius, 0, sigma_x)
prob_y = norm.cdf(y + radius, 0, sigma_y) - norm.cdf(y - radius, 0, sigma_y)
return prob_x * prob_y
炸弹命中概率:根据炸弹与潜艇的距离计算命中概率。如果炸弹在潜艇的杀伤半径内,则命中概率较高,否则随着距离增加命中概率下降。
# 计算炸弹的命中概率
def calc_hit_prob(bomb_pos, sub_pos, base_prob, rem_prob):
dist = np.sqrt((bomb_pos[0] - sub_pos[0]) ** 2 + (bomb_pos[1] - sub_pos[1]) ** 2)
if dist <= radius:
return base_prob * rem_prob
else:
return base_prob * rem_prob / (dist / radius)
3. 三种投弹策略
- 策略一:斜方向投弹
- 沿 3x3 矩阵的对角线投放炸弹。逐步排除未命中的区域,从而提高后续投弹的命中概率。
def diagonal_bombing(positions, sub_pos, base_prob):
results = []
rem_prob = 1.0
diagonal_pos = [positions[0], positions[4], positions[8]]
for pos in diagonal_pos:
hit_prob = calc_hit_prob(pos, sub_pos, base_prob, rem_prob)
results.append(hit_prob)
excl_prob = calc_excluded_prob(pos[0], pos[1], sigma_x, sigma_y, radius)
rem_prob -= excl_prob
base_prob *= rem_prob
while len(results) < 9:
results.append(0)
return results
策略二:中心扩展投弹
- 先投放中心炸弹,再投放上下左右的炸弹,最后投放四角的炸弹。这种策略对称性强,适合潜艇更可能位于中心的情况。
def center_out_bombing(positions, sub_pos, base_prob):
results = []
rem_prob = 1.0
center_pos = positions[4]
neighbors = [positions[1], positions[3], positions[5], positions[7]]
corners = [positions[0], positions[2], positions[6], positions[8]]
hit_prob = calc_hit_prob(center_pos, sub_pos, base_prob, rem_prob)
results.append(hit_prob)
excl_prob = calc_excluded_prob(center_pos[0], center_pos[1], sigma_x, sigma_y, radius)
rem_prob -= excl_prob
base_prob *= rem_prob
for pos in neighbors + corners:
hit_prob = calc_hit_prob(pos, sub_pos, base_prob, rem_prob)
results.append(hit_prob)
excl_prob = calc_excluded_prob(pos[0], pos[1], sigma_x, sigma_y, radius)
rem_prob -= excl_prob
base_prob *= rem_prob
return results
策略三:顺时针/逆时针投弹
- 按照顺时针或逆时针顺序投放炸弹,从边缘向内逐渐覆盖潜艇的可能位置。
def circular_bombing(positions, sub_pos, base_prob, clockwise=True):
results = []
rem_prob = 1.0
if clockwise:
order = [positions[0], positions[1], positions[2], positions[5], positions[8],
positions[7], positions[6], positions[3], positions[4]]
else:
order = [positions[0], positions[3], positions[6], positions[7], positions[8],
positions[5], positions[2], positions[1], positions[4]]
for pos in order:
hit_prob = calc_hit_prob(pos, sub_pos, base_prob, rem_prob)
results.append(hit_prob)
excl_prob = calc_excluded_prob(pos[0], pos[1], sigma_x, sigma_y, radius)
rem_prob -= excl_prob
base_prob *= rem_prob
return results
4. 优化策略
- 使用粒子群优化(PSO)算法来调整投弹间隔(
a
和b
)以及引爆深度(Z_trigger
),以找到最优参数组合,使总命中概率最大化。
# 优化目标函数,用于计算总命中概率
def optimize_strategy(x):
a, b, Z_trigger = x
sub_pos = generate_sub_position()
positions = bomb_positions()
base_prob = Z_trigger / 200.0
diag_probs = diagonal_bombing(positions, sub_pos, base_prob)
center_probs = center_out_bombing(positions, sub_pos, base_prob)
circ_probs = circular_bombing(positions, sub_pos, base_prob, clockwise=True)
total_prob = sum(diag_probs) + sum(center_probs) + sum(circ_probs)
return -total_prob # 取负值用于最小化问题
# 使用PSO优化a, b, Z_trigger
lb = [20, 20, 170]
ub = [60, 60, 190]
best_params, best_prob = pso(optimize_strategy, lb, ub, swarmsize=30, maxiter=50)
最后,根据优化结果选择最优策略并进行排序。
strategies = [("斜方向投弹", sum(diag_probs)),
("中心扩展投弹", sum(center_probs)),
("顺时针投弹", sum(circ_probs))]
sorted_strategies = sorted(strategies, key=lambda x: x[1], reverse=True)
for i, (name, prob) in enumerate(sorted_strategies):
print(f"第 {i + 1} 名: {name}, 总命中概率: {prob:.4f}")
通过分析潜艇的定位误差,调整投弹阵列的间隔和定深引信的引爆深度,结合三种不同的投弹策略(斜方向、中心扩展、顺时针/逆时针),并使用粒子群优化算法进行参数优化,我们成功设计出了最优的投弹方案,使潜艇被命中的概率最大化。
一问、二问解题思路可看我历史文章