Skip to content
Snippets Groups Projects
Unverified Commit 2bf6c0e5 authored by Michiel Cottaar's avatar Michiel Cottaar
Browse files

Add AbstractAlternativeBlocks

parent dfc27997
No related branches found
No related tags found
1 merge request!5Resolve "Allow slice selection"
...@@ -28,8 +28,8 @@ export variables, make_generic, @defvar, get_pulse, get_readout, get_pathway, ge ...@@ -28,8 +28,8 @@ export variables, make_generic, @defvar, get_pulse, get_readout, get_pathway, ge
import .Components: InstantPulse, ConstantPulse, SincPulse, GenericPulse, InstantGradient, SingleReadout, ADC, CompositePulse, edge_times import .Components: InstantPulse, ConstantPulse, SincPulse, GenericPulse, InstantGradient, SingleReadout, ADC, CompositePulse, edge_times
export InstantPulse, ConstantPulse, SincPulse, GenericPulse, InstantGradient, SingleReadout, ADC, CompositePulse, edge_times export InstantPulse, ConstantPulse, SincPulse, GenericPulse, InstantGradient, SingleReadout, ADC, CompositePulse, edge_times
import .Containers: ContainerBlock, start_time, end_time, waveform, waveform_sequence, events, BaseBuildingBlock, BuildingBlock, Wait, BaseSequence, nrepeat, Sequence, AlternativeBlocks, match_blocks!, get_index_single_TR, iter_blocks, iter_instant_gradients, iter_instant_pulses import .Containers: ContainerBlock, start_time, end_time, waveform, waveform_sequence, events, BaseBuildingBlock, BuildingBlock, Wait, BaseSequence, nrepeat, Sequence, AbstractAlternativeBlocks, get_alternatives_name, get_alternatives_options, AlternativeBlocks, match_blocks!, get_index_single_TR, iter_blocks, iter_instant_gradients, iter_instant_pulses
export ContainerBlock, start_time, end_time, waveform, waveform_sequence, events, BaseBuildingBlock, BuildingBlock, Wait, BaseSequence, nrepeat, Sequence, AlternativeBlocks, match_blocks!, get_index_single_TR, iter_blocks, iter_instant_gradients, iter_instant_pulses export ContainerBlock, start_time, end_time, waveform, waveform_sequence, events, BaseBuildingBlock, BuildingBlock, Wait, BaseSequence, nrepeat, Sequence, AbstractAlternativeBlocks, get_alternatives_name, get_alternatives_options, AlternativeBlocks, match_blocks!, get_index_single_TR, iter_blocks, iter_instant_gradients, iter_instant_pulses
import .Pathways: Pathway import .Pathways: Pathway
export Pathway export Pathway
......
...@@ -4,6 +4,17 @@ import ..Abstract: ContainerBlock ...@@ -4,6 +4,17 @@ import ..Abstract: ContainerBlock
import ...BuildSequences: fixed import ...BuildSequences: fixed
import ...Variables: @defvar, make_generic, apply_simple_constraint! import ...Variables: @defvar, make_generic, apply_simple_constraint!
"""
Parent type for all blocks that can take different MR sequence components between multiple repetitions of the sequence.
They can be extended into their individual components using `adjust(<name>=:all)`.
Each subtype of [`AbstractAlternativeBlock`](@ref) needs to implement two methods:
- [`get_alternatives_name`](@ref): returns the `name` used to identify this block in `adjust`
- [`get_alternatives_options`](@ref): returns a dictionary mapping the name of the different options to a [`ContainerBlock`](@ref) with the actual sequence building block.
"""
abstract type AbstractAlternativeBlocks <: ContainerBlock end
""" """
AlternativeBlocks(name, blocks) AlternativeBlocks(name, blocks)
...@@ -11,19 +22,35 @@ Represents a part of the sequence where there are multiple possible alternatives ...@@ -11,19 +22,35 @@ Represents a part of the sequence where there are multiple possible alternatives
Variables can be matched across these alternatives using [`match_blocks!`](@ref). Variables can be matched across these alternatives using [`match_blocks!`](@ref).
The `name` is a symbol that is used to identify this `AlternativeBlocks` in the broader sequence. The `name` is a symbol that is used to identify this `AlternativeBlocks` in the broader sequence (as in `adjust`).
""" """
struct AlternativeBlocks <: ContainerBlock struct AlternativeBlocks <: AbstractAlternativeBlocks
name :: Symbol name :: Symbol
options :: Dict{Any, <:ContainerBlock} options :: Dict{Any, <:ContainerBlock}
end end
AlternativeBlocks(name::Symbol, options_vector::AbstractVector) = AlternativeBlocks(name, Dict(index => value for (index, value) in enumerate(options_vector))) AlternativeBlocks(name::Symbol, options_vector::AbstractVector) = AlternativeBlocks(name, Dict(index => value for (index, value) in enumerate(options_vector)))
Base.getindex(alt::AlternativeBlocks, index) = alt.options[index] """
Base.length(alt::AlternativeBlocks) = length(alt.options) get_alternatives_name(alternative_block)
Get the name with which any [`AbstractAlternativeBlocks`](@ref) will be identified in a call to `adjust`.
"""
get_alternatives_name(alt::AlternativeBlocks) = alt.name
@defvar duration(alt::AlternativeBlocks) = maximum(variables.duration.(values(alt.options))) """
get_alternatives_options(alternative_block)
Get the options available for a [`AbstractAlternativeBlocks`](@ref).
"""
get_alternatives_options(alt::AlternativeBlocks) = alt.options
Base.getindex(alt::AbstractAlternativeBlocks, index) = get_alternatives_options(alt)[index]
Base.length(alt::AbstractAlternativeBlocks) = length(get_alternatives_options(alt))
Base.keys(alt::AbstractAlternativeBlocks) = keys(get_alternatives_options(alt))
Base.values(alt::AbstractAlternativeBlocks) = values(get_alternatives_options(alt))
@defvar duration(alt::AbstractAlternativeBlocks) = maximum(variables.duration.(values(alt.options)))
""" """
match_blocks!(alternatives, function) match_blocks!(alternatives, function)
...@@ -32,8 +59,11 @@ Matches the outcome of given `function` on each of the building blocks in [`Alte ...@@ -32,8 +59,11 @@ Matches the outcome of given `function` on each of the building blocks in [`Alte
For example, `match_blocks!(alternatives, duration)` will ensure that all the alternative building blocks have the same duration. For example, `match_blocks!(alternatives, duration)` will ensure that all the alternative building blocks have the same duration.
""" """
function match_blocks!(alternatives::AlternativeBlocks, func) function match_blocks!(alternatives::AbstractAlternativeBlocks, func)
options = [values(alternatives.options)...] options = [values(get_alternatives_options(alternatives.options))...]
if length(options) <= 1
return
end
baseline = func(options[1]) baseline = func(options[1])
for other_block in options[2:end] for other_block in options[2:end]
apply_simple_constraint!(func(other_block), baseline) apply_simple_constraint!(func(other_block), baseline)
...@@ -41,7 +71,7 @@ function match_blocks!(alternatives::AlternativeBlocks, func) ...@@ -41,7 +71,7 @@ function match_blocks!(alternatives::AlternativeBlocks, func)
end end
fixed(alt::AlternativeBlocks) = AlternativeBlocks(alt.name, Dict(key=>fixed(value) for (key, value) in alt.options)) fixed(alt::AlternativeBlocks) = AlternativeBlocks(alt.name, Dict(key=>fixed(value) for (key, value) in alt.options))
make_generic(alt::AlternativeBlocks) = AlternativeBlocks(alt.name, Dict(key=>make_generic(value) for (key, value) in alt.options)) make_generic(alt::AbstractAlternativeBlocks) = AlternativeBlocks(get_alternatives_name(alt), get_alternatives_options(alt))
end end
\ No newline at end of file
...@@ -7,6 +7,6 @@ include("alternatives.jl") ...@@ -7,6 +7,6 @@ include("alternatives.jl")
import .Abstract: ContainerBlock, start_time, end_time, iter_blocks, iter_instant_gradients, iter_instant_pulses import .Abstract: ContainerBlock, start_time, end_time, iter_blocks, iter_instant_gradients, iter_instant_pulses
import .BuildingBlocks: BaseBuildingBlock, BuildingBlock, Wait, waveform, waveform_sequence, events, ndim_grad import .BuildingBlocks: BaseBuildingBlock, BuildingBlock, Wait, waveform, waveform_sequence, events, ndim_grad
import .BaseSequences: BaseSequence, Sequence, nrepeat, get_index_single_TR import .BaseSequences: BaseSequence, Sequence, nrepeat, get_index_single_TR
import .Alternatives: AlternativeBlocks, match_blocks! import .Alternatives: AbstractAlternativeBlocks, get_alternatives_name, get_alternatives_options, AlternativeBlocks, match_blocks!
end end
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment