Skip to content

Instantly share code, notes, and snippets.

@DhairyaLGandhi
Created February 6, 2020 18:42
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save DhairyaLGandhi/0beb8ef19feb0cdb371f777d48defbfd to your computer and use it in GitHub Desktop.
Save DhairyaLGandhi/0beb8ef19feb0cdb371f777d48defbfd to your computer and use it in GitHub Desktop.
using MacroTools: @forward
struct Imm{T,N} <: AbstractArray{T,N}
data::AbstractArray{T,N}
optinds::Dict{T,T}
iscommited::Ref{Bool}
end
# struct IsCommitted end
# struct IsNotCommitted end
# iscommited(arr::Imm{<:Any,<:Any, ::Base.RefValue{true}}) = IsCommitted()
# iscommited(arr::Imm{<:Any,<:Any, ::Base.RefValue{false}}) = IsNotCommitted()
iscommited(arr::Imm) = arr.iscommited[]
@forward Imm.data Base.show, Base.size
Imm(arr::AbstractArray{T,N}) where {T,N} = Imm(arr, Dict{T,T}(), Ref(true))
Imm(arr::Imm) = Imm(arr.data, Dict{T,T}(), Ref(true))
Base.IndexStyle(::Type{<:Imm}) = IndexLinear()
function Base.getindex(arr::Imm, i::Int)
if iscommited(arr)
arr.data[i]
else
haskey(arr.optinds, i) && return arr.optinds[i]
arr.data[i]
end
end
# getindex(arr::Imm, i::Int) = _getindex(arr, i, iscommited(arr))
# _getindex(arr::Imm, i, ::IsCommitted) = Base.getindex(arr.data, i)
# function _getindex(arr::Imm, i, ::IsNotCommitted)
# haskey(arr.optinds, i) && return arr.optinds[i]
# arr.data[i]
# end
Base.similar(arr::Imm) = Imm(similar(arr.data))
Base.setindex!(arr::Imm, val, ind) = (arr.iscommited[] = false; arr.optinds[ind] = val)
Base.setindex(arr::Imm, val, ind) = (arr.iscommited[] = false; arr.optinds[ind] = val)
function commit!(arr)
for (k,v) in arr.optinds
arr.data[k] = v
end
Imm(arr)
end
function Base.getindex(arr::Imm, i::Union{Base.UnitRange, Base.OneTo})
makeopts!(arr)
arr.data[i]
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment