# Defining variable with varying number of index sets

**URL:** <https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478>\
**Category:** Optimization (Mathematical)\
**Tags:** jump\
**Created:** [April 28, 2025, 6:46am UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478 "2025-04-28T06:46:34Z")\
**Posts on this page:** 9\
**Page:** 1

<div class="post-metadata">

**Author:** ![Magnus\_Lilledahl](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/magnus_lilledahl/32/51079_2.png) [@Magnus\_Lilledahl](https://discourse.julialang.org/u/Magnus_Lilledahl)\
**Post date:** [April 28, 2025, 6:46am UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/1 "2025-04-28T06:46:34Z")

</div>

I want to create a JuMP variable with the syntax

```julia
@variable(model, [U])

```

such that it is equivalent to

```julia
@variable(model, [S,T])

```

How can I ‘pack’ `S,T `into `U` such that it exapnds to `S,T` in the `@variable` syntax?

What I would like is to have a function `get_index_sets(A)` that can dispatch on different types of `A` to give different sets of indexes

```julia
U = get_index_set(A)
# U could then be 1:N for one type of A and (say) 1:N, ["high", "low"] for another type
@variable(model, x[U])

```

I tried

```julia
U = [(s,t) for s in S for t in T]

```

But this gives 1-D array of indicies instead of a 2D array?

Or is this not possible so I would have to write the variable creation seperately for each case?

---

<div class="post-metadata">

**Author:** ![WalterMadelim](https://avatars.discourse-cdn.com/v4/letter/w/3e96dc/32.png) [@WalterMadelim](https://discourse.julialang.org/u/WalterMadelim)\
**Post date:** [April 28, 2025, 11:34am UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/2 "2025-04-28T11:34:41Z")

</div>

Why do you want to do this, and the “dispatch”.  
Sounds a bit complicated.  
Decision variables are typically of type Float64, which should be sufficient in practice.

In my opinion, you should decide which quantity should be modeled as a `variable` judiciously.  
And for the rest you can use `@expression`, which is a very powerful macro.

e.g.  
`@variable(model, U[1:4])`  
`@expression(model, S, U[1:2])`  
`@expression(model, T, U[3:4])`

or you can do  
`@variable(model, S[1:2])`  
`@variable(model, T[1:2])`  
`@expression(model, U, [S; T])`

> [@Magnus\_Lilledahl](#):
>
> But this gives 1-D array of indicies instead of a 2D array?

```julia
julia> [(i, j) for i in 1:3, j in 1:2]
3×2 Matrix{Tuple{Int64, Int64}}:
 (1, 1) (1, 2)
 (2, 1) (2, 2)
 (3, 1) (3, 2)

julia> [(i, j) for i in 1:3 for j in 1:2]
6-element Vector{Tuple{Int64, Int64}}:
 (1, 1)
 (1, 2)
 (2, 1)
 (2, 2)
 (3, 1)
 (3, 2)

```

---

<div class="post-metadata">

**Author:** ![odow](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/odow/32/28685_2.png) [@odow](https://discourse.julialang.org/u/odow)\
**Post date:** [April 28, 2025, 8:53pm UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/3 "2025-04-28T20:53:50Z")

</div>

Hi @Magnus_Lilledahl,

You cannot do this via the built-in JuMP syntax.

Take a read of [Variables · JuMP](https://jump.dev/JuMP.jl/stable/manual/variables/#User-defined-containers)

You do not need to use the built-in JuMP containers. They’re intended to help common use-cases. If you want something else, you’ll need to implement it yourself.

---

<div class="post-metadata">

**Author:** ![slwu89](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/slwu89/32/217323_2.png) [@slwu89](https://discourse.julialang.org/u/slwu89)\
**Post date:** [April 28, 2025, 10:59pm UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/4 "2025-04-28T22:59:38Z")

</div>

Just my 2 cents, but I often find when I am struggling to think of how to use the existing JuMP syntax to set up a model, it means I’m thinking about it wrong and a change of perspective can make it clearer how to model it, for example seeing it as a graph with decision variables on edges and nodes, or some other data structure such as state-task networks, activity networks, etc. The possibilities really are quite endless.

---

<div class="post-metadata">

**Author:** ![odow](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/odow/32/28685_2.png) [@odow](https://discourse.julialang.org/u/odow)\
**Post date:** [April 28, 2025, 11:06pm UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/5 "2025-04-28T23:06:45Z")

</div>

> [@slwu89](#):
>
> The possibilities really are quite endless.

👍

This is the strength and limitation of JuMP at the same time. It is possible to write some very nice code that elegantly models the problem. But it’s also hard to provide generic advice for new problems because there isn’t a one-size-fits-all approach. The built-in containers (`Array`, `DenseAxisArray` and `SparseAxisArray`) are most commonly useful, but they aren’t always the best data structures.

---

<div class="post-metadata">

**Author:** ![slwu89](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/slwu89/32/217323_2.png) [@slwu89](https://discourse.julialang.org/u/slwu89)\
**Post date:** [April 29, 2025, 12:55am UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/6 "2025-04-29T00:55:58Z")

</div>

Yeah. The subtle shift in perspective is really important for modeling. It’s what I was trying to get across with my blog post over at AlgebraicJulia about integrating JuMP into C-Sets.

---

<div class="post-metadata">

**Author:** ![Magnus\_Lilledahl](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/magnus_lilledahl/32/51079_2.png) [@Magnus\_Lilledahl](https://discourse.julialang.org/u/Magnus_Lilledahl)\
**Post date:** [April 29, 2025, 6:00am UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/7 "2025-04-29T06:00:10Z")

</div>

@odow Thanks for the clear answer (that it is not possible) and suggestion about the custom containers, I had forgotten (I think it docs says something like “…a feature often overlook by beginners…” 😀 ) about that possibility - and will check it out.

Just to be clear about my original plan (@WalterMadelim ): What I want is a piece of software where I can easily change between deterministic and stochastic modelling. To try to elaborate (in a minimal way), I have (something like) two different structs

```julia
struct Deterministic <: Indexstruct
   periods::Int
end

struct Stochastic <: Indexstruct
   periods::Int
   scenarios:Vector{Any}
end

```

Then somewhere in my code I would call a function to define the variables

```julia
function set_variables(ind::Indexstruct)
    index_sets = indices(ind)
    @variable(model, [index_sets])
end

# Users inputs one of these
d = Deterministic(10)
s = Stochastic(10,["high", "low"])

# and the system calls
set_variables(d)
# or set_variables(s)

```

and the `indices` function will dispatch on the type of index struct

```julia
function indices(d::Deterministic)
    return 1:d.periods
end

function inidices(s::Stochastic)
    return [1:s.periods, s.scenarios]
end
# The syntax in this last expression does not work because the @variable macro 
# will interpret this as two elements with the indices being a OneTo object and 
# a vector. As Odow points out, it seems not to be possible

```

A workaround could be to dispatch on the `set_variables` function

```julia
function set_variables(d::Deterministic)
   @variable(model, [1:d.periods])
end

function set_variables(s::Stochastic)
   @variable(model, [1:s.periods, s.scenarios]
end

```

This would lead to a lot of repeated code (there are many `@variable` calls), but maybe a worth it? Or maybe that I am struggling with the design means I should reconsider my data structure as @slwu89 points out…

---

<div class="post-metadata">

**Author:** ![odow](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/odow/32/28685_2.png) [@odow](https://discourse.julialang.org/u/odow)\
**Post date:** [April 29, 2025, 6:42am UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/8 "2025-04-29T06:42:16Z")

</div>

> I think it docs says something like “…a feature often overlook by beginners

See the link I shared above 😄

You could do:

```julia
function indices(d::Deterministic)
    return [1:d.periods, 1:1]
end

```

a deterministic problem is also a stochastic problem with one scenario.

> A workaround could be to dispatch on the `set_variables` function

See: [Design patterns for larger models · JuMP](https://jump.dev/JuMP.jl/stable/tutorials/getting_started/design_patterns_for_larger_models/)

For other inspiration, see:

- SDDP.jl. We ask the user to build a deterministic single-scenario problem, and then they provide a function which parameterizes the problem for each scenario
- It’s unmaintained now, but you might also take inspiration from [GitHub - martinbiel/StochasticPrograms.jl: Julia package for formulating and analyzing stochastic recourse models.](https://github.com/martinbiel/StochasticPrograms.jl)

---

<div class="post-metadata">

**Author:** ![slwu89](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/slwu89/32/217323_2.png) [@slwu89](https://discourse.julialang.org/u/slwu89)\
**Post date:** [April 29, 2025, 2:15pm UTC](https://discourse.julialang.org/t/defining-variable-with-varying-number-of-index-sets/128478/9 "2025-04-29T14:15:48Z")

</div>

The aforementioned blog post I wrote about embedding JuMP models in a C-Set (a type of data structure from applied category theory generalizing graphs and databases) is here, where I show how to formulate the simple multi-commodity flow problem in this way [JuMP-ing with AlgebraicJulia II: A practical optimization model – AlgebraicJulia blog](https://blog.algebraicjulia.org/post/2025/03/optim-netflow/)

If you’ve never seen a C-Set before, this is a nice place to start [Graphs and C-sets I: What is a graph? – AlgebraicJulia blog](https://blog.algebraicjulia.org/post/2020/09/cset-graphs-1/)
