在CVXPY中,如何创建一个布尔变量来检查是否发生了变化?



我有一个问题,当使用CVXPY,我希望计算输入流的计算在我的程序中的一个额外的约束,我有一个选择布尔变量,我用它来确定流量,这反过来被用来重塑一个向量,以适应我需要的。

在这个意义上,我估计计算储层流动在24小时内,所以选择的流在7期不同的时间段(分成30分钟间隔),我试图排序的问题是,通常情况下,可能需要也许4 30分钟时间从说15 l/s到所需的17个l/s流量可最终我的计算有很大影响较小的表面区域也就是我希望能够消除。

Example output currently for 1 period out of 7 (00:00 - 08:00):
[120 120 120 120 120 120 120 120 120 120 120 120 120 120 120 120]
# Imagine our ramp rate is actually 0.5l/s per 30 minutes and currently at 118l/s
Expected output:
[118 118.5 119 119.5 120 120 120 120 120 120 120 120 120 120 120 120]

我希望上面的例子对我想要达到的目标有意义

请参阅下面我目前的解决方案,我已经实现了没有针对当前问题开发的斜坡率。

FACTOR = 1/self.SURFACE_AREA
input_flow_matrix=np.zeros((max(period_lengths),len(period_lengths)))
for i,l in enumerate(period_lengths):
input_flow_matrix[:l,i]=1
selection = cp.Variable(shape=cost_.shape,boolean=True)
assignment_constraint = cp.sum(selection,axis=1) == 1
input_flow_= cp.sum(cp.multiply(flow_,selection),axis=1)
input_flow_vector=cp.vec(cp.multiply(input_flow_matrix,np.ones((max(period_lengths), 1)) @ cp.reshape(input_flow_,(1,len(period_lengths)))))
res_flow= (input_flow_vector-cp.vec(out_flow_))
net_volume = res_flow * 1.8
res_level=cp.cumsum(net_volume) * FACTOR + initial_level
volume_= cp.sum(cp.multiply(volume_,selection))
volume_constraint = volume_ >= v_min
min_level_constraint = res_level >= min_level
max_level_constraint = res_level <= max_level
constraints = [assignment_constraint, max_level_constraint, min_level_constraint, volume_constraint]
cost_ = cp.sum(cp.multiply(cost_,selection))
assign_prob = cp.Problem(cp.Minimize(cost_),constraints)
assign_prob.solve(solver=cp.CPLEX, verbose=False)

我在这里的假设是包括一个布尔变量,该变量将指示流量是否在我的7个周期内发生变化,这来自input_flow_变量。然而,我只是不确定如何实际开发一个好的解决方案,这是需要在一个矩阵或类似的东西吗?如有任何帮助,不胜感激。

如果有助于再现,我可以提供数据。

如果我正确理解了你的问题,你应该重新实现考虑斜坡率的flow_。我没有对一般情况进行建模,但以下内容应该适用于您的情况。

# delta flow, models the 1-hop influence of certain selection (next )
delta_flow_ = [5, 5, 5, 5, 4.5, 5, 4.5]
selection_of_previous_period = cp.hstack([selection[0:-1, :], np.zeros((1, num_of_pumps))])  # assume selection is flase at the beginning of the day
existence_of_delta_flow = cp.multiply(1-selection_of_previous_period, selection)  # delta flow exist when previous period is close and now is open
input_flow_ = input_flow_ - cp.sum(cp.multiply(delta_flow_, existence_of_delta_flow), axis=1)
# delta delta flow, models the 2-hop influence of certain selection
delta_delta_flow_ = [0, 0, 0, 0, 0, 0.5, 0]
selection_of_previous_period2 = cp.hstack([selection[0:-2, :], np.zeros((2, num_of_pumps))])  # assume selection is flase at the beginning of the day
# delta_delta_flow[i] exist if selection[i-2] is False, and selection[i-1] is True, and selection[i] is True
# the delta_delta_flow_[6] is 0.5, which means if selection[4]=False (pump not selected in period[4], indexing from 0)
# and selection[5]=True (pump selected in period[5]) and and selection[6]=True
# delta_delta_flow[i] is non_zero when the length period[i-1]<4*30min
existence_of_delta_delta_flow = existence_of_delta_flow = cp.multiply(cp.multiply(1-selection_of_previous_period2, selection_of_previous_period), selection)
input_flow_ = input_flow_ - cp.sum(cp.multiply(delta_delta_flow_, existence_of_delta_delta_flow), axis=1)
# For general case, you may need "delta_delta_delta_flow_", which model the 3-hop influence of certain selection

另外,考虑到斜坡率,我认为volume_可能也需要重新实现。你可以模仿我的代码,自己做。

最新更新