3.3.13. 条件式

条件式は,添字の動く範囲を制限する機能を有します. 次の例では,定数 a[1], a[2] に -1 を,a[3] に 1 を設定しています.:

i = Element(value=[1, 2, 3])
a = Parameter(index=i)
a[i<=2] = -1
a[i>=3] = 1

条件式が一つの式の複数箇所に登場する場合,条件式は一度保存したものを使用する必要があります.

i = Element(value=[1, 2, 3])
a = Parameter(index=i)
x = Variable(index=i)
i2 = i<=2
ax = a[i2] + x[i2]

次の例は誤りです.:

ax = a[i<=2] + x[i<=2]

条件付けられた添字と条件付けられていない添字を混在することはできません. 次の例はいずれも誤りです.:

ax = a[i] + x[i<=2]
ax = a[i<=2] + x[i]

条件式には等号 ==,等式付不等号 <= >=,不等号 < >,不一致 != 演算子が使用できます (制約式に使用できるのは,等号と等式付不等号のみです). 次の例では,定数 asum の値を定数 a[i] の中で 0 より大きいものの和 \(\sum_{a_{i} > 0} a_{i}\) で定めています.:

i = Element(value=[1, 2, 3])
a = Parameter(index=i, value={1: 10, 2: -20, 3: 30})
apos = a[i]>0
asum = Sum(a[apos], apos)

上の例では,Sum 関数の第二引数を省略することで一度に記述することができます.:

asum = Sum(a[a[i]>0])

不等号 < > は添字に対する集合の所属有無を表現する演算子としても使用されます. 以下の例では,定数 a[1], a[2] に -1 を,a[3] に 1 を設定しています.:

i = Element(value=[1, 2, 3])
T = Set(value=[1, 2])
a = Parameter(index=i)
a[i<T] = -1  # i が T に含まれる場合
a[i>T] = 1   # i が T に含まれない場合

集合を用いずに直接記述することもできます.:

i = Element(value=[1, 2, 3])
a = Parameter(index=i)
a[i<[1, 2]] = -1  # i が [1, 2] に含まれる場合
a[i>[1, 2]] = 1   # i が [1, 2] に含まれない場合

条件式同士を演算子 &, | で連結することができます.それぞれ,and, or を意味します. 次の例では,定数 b[1], b[4] に -1 を,b[2], b[3] に 1 を設定しています.:

i = Element(value=[1, 2, 3, 4])
b = Parameter(index=i)
b[(i<=1) | (i>=4)] = -1
b[(i>=2) & (i<=3)] = 1

演算子の優先順位により,それぞれの条件式を括弧でくくる必要があることに注意してください.

多次元の条件式を作ることもできます.:

i = Element(value=[1, 2, 3])
j = Element(value=[1, 2, 3])
x = Variable(index=(i,j))
print(x[i<j])

この出力は次のようになります.:

x:
x[1,2]
x[1,3]
x[2,3]

多次元の条件式の一部の次元を用いる場合は () で必要な次元だけを取り出す必要があります. 次の例では二次元の条件式 i<j の 1 次元目を使用して変数 y にアクセスしています.:

i = Element(value=[1, 2, 3])
j = Element(value=[1, 2, 3])
x = Variable(index=(i,j))
y = Variable(index=i)
ij = i<j
print(x[ij] + y[ij(0)])

次元は 0 から数えます.この出力は次のようになります.:

(x[(i<j)]+y[(i<j)(0)]):
x[1,2]+y[1]
x[1,3]+y[1]
x[2,3]+y[2]

条件式に変数や式を用いることはできません.次の記述は誤りです.:

i = Element(value=[1, 2])
x = Variable(index=i)
y = Variable(index=i)
xpos = x[i] >= 0
3*x[xpos] + 2*y[xpos] == 0

3.3.13.1. Condition 関数

複雑な条件式を作成するために Condition 関数を用いることができます. 次の記述はいずれも同じ意味を持ちます.:

i = Element(value=[1, 2, 3])
i1 = i>1
i = Element(value=[1, 2, 3])
i1 = Condition(i, i>1)

次の例では二次元集合 IJ に対して一次元目が 1 である条件式を作成しています.:

ij = Element(value=[(1,3), (1,4), (2,3)])
ij0 = ij(0)==1

ここで注意すべきは ij0 は一次元の条件式となるので,ij0 は 1 の範囲のみを動きます. 上の例は以下と同じ意味を持ちます.:

ij = Element(value=[(1,3), (1,4), (2,3)])
ij0 = Condition(ij(0), ij(0)==1)

二次元の条件式を作成するには次のようにします.:

ij = Element(value=[(1,3), (1,4), (2,3)])
ij0 = Condition(ij, ij(0)==1)

ここで ij0 は二次元の条件式なので,範囲 (1,3) と (1,4) を動くことになります.

第二引数に条件式のタプルを与えることによって複数の条件を考慮することもできます.:

i = Element(value=[1, 2, 3])
i2 = Condition(i, (1<i, i<3))
i = Element(value=[1, 2, 3])
j = Element(value=[4, 5])
ij = Condition((i,j), (i!=2, j>4))

このように Condition 関数を用いることによって複雑な条件式を作成することができるようになります.