Pyomo: минимизировать максимальное значение в векторе - PullRequest
1 голос
/ 08 мая 2019

Я оптимизирую поведение аккумуляторной батареи в сочетании с солнечной фотоэлектрической энергией, чтобы получить максимально возможный доход.Теперь я хочу добавить еще один источник дохода: Пиковая экономия (или снижение спроса)

Мой подход заключается в следующем:

  • Рядом с ценой за кВтч, платит промышленный потребительдля максимальной величины мощности (кВт), которую он извлекал из сетки за один период (i = 1: конец), так называемые платежи по требованию
  • Эта максимальная сумма находится в векторе P_Grid = P_GridLoad (энергия self-потребляется из сетки) + P_GridBatt (энергия, используемая для зарядки батареи)
  • Существует вектор цен, который сообщает цену за кВт для всех моментов времени
  • Теперь я хочу сгенерироватьвектор P_GridMax, который равен нулю для всех точек времени, но в момент, когда происходит максимальное значение P_Grid (тогда оно равно max (P_Grid).
  • Таким образом, вектор P_GridMax состоит из нулей и одного ненулевого элемента (не более)!)
  • Теперь я могу умножить этот вектор на вектор цен, суммировать по всем моментам времени и получать начисленные расходы по требованию
  • По вкл.Вводя этот вектор в цель моей модели, я могу минимизировать эти расходы

Теперь, кто-нибудь видит решение о том, как сформулировать такое ограничение (P_GridMax)?Я уже обновил свою целевую функцию и определил P_Grid.Любой другой подход также приветствуется.

Это актуальная часть моей модели, где P_xxx = векторы потока мощности, C_xxx = векторы цены, ...

m.P_Grid = Var(m.i_TIME, within = NonNegativeReals)
m.P_GridMax = Var(m.i_TIME, within = NonNegativeReals)


# Minimize electricity bill
def Total_cost(m):
    return ... + sum(m.P_GridMax[i] * m.C_PowerCosts[i] for i in m.i_TIME) - ...
m.Cost = Objective(rule=Total_cost)


## Peak Shaving constraints
def Grid_Def(m,i):
    return m.P_Grid[i] = m.P_GridLoad[i] + m.P_GridBatt[i]
m.Bound_Grid = Constraint(m.i_TIME,rule=Grid_Def)

def Peak_Rule(m,i):
    ????
    ????
    ????
    ????
m.Bound_Peak = Constraint(m.i_TIME,rule=Peak_Rule)

Заранее большое спасибо!Пожалуйста, имейте в виду, что у меня очень мало опыта в программировании на python / pyomo, я был бы очень признателен, если бы вы дали подробные объяснения:)

Best, Mathias

1 Ответ

1 голос
/ 08 мая 2019

Вот один из способов сделать это:

введите двоичную вспомогательную переменную ismax[i] for i in i_TIME. Эта переменная равна 1, если максимум получается в периоде i, и 0 в противном случае. Тогда, очевидно, у вас есть ограничение sum(ismax[i] for i in i_TIME) == 1: максимум должен быть достигнут ровно за один период.

Теперь вам нужно два дополнительных ограничения:

  1. если ismax[i] == 0, то P_GridMax[i] == 0.
  2. если ismax[i] == 1, то для всех j in i_TIME должно быть P_GridMax[i] >= P_GridMax[j].

Лучший способ сформулировать это - использовать индикаторные ограничения, но я не знаю Pyomo, поэтому не знаю, поддерживает ли он это (полагаю, да, но я не знаю, как их написать). Так что вместо этого я приведу формулировку с большой буквы М.

Для этой формулировки вам нужно определить константу M, чтобы P_Grid[i] не мог превышать это значение для любого i. При этом первое ограничение становится

P_GridMax[i] <= M * ismax[i]

Это ограничение заставляет P_GridMax[i] равняться 0, если ismax[i] == 1. Для ismax[i] == 1 это избыточно. Второе ограничение будет для всех j in i_TIME

P_GridMax[i] + M * (1 - ismax[i]) >= P_Grid[j]

Если ismax[i] == 0, то левая часть этого ограничения составляет не менее M, поэтому по определению M оно будет выполнено независимо от значения P_GridMax[i] (первые силы ограничения P_Grid[i] == 0 в этом случае). Для ismax[i] == 1 левая часть ограничения становится просто P_GridMax[i], именно то, что мы хотим.

...