-
Notifications
You must be signed in to change notification settings - Fork 21
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Manifest VariableTypes (Singleton model) and new FMD #783
Comments
Just for reference: https://docs.julialang.org/en/v1/manual/types/#man-singleton-types-1 |
Singleton types can work with current Pose2 for example: struct Pose2 <: IncrementalInference.InferenceVariable
dims::Int
manifolds::Tuple{Symbol,Symbol,Symbol}
Pose2() = new(3, (:Euclid, :Euclid, :Circular))
end as struct Pose2 end
getdims(::Pose2) = 3
getmanifolds(::Pose2) = (:Euclid, :Euclid, :Circular) |
Also see JuliaRobotics/RoME.jl#244 on standardizing with Manifolds.jl. |
Copy from Slack, @GearsAD asked if this was workable: # TODO: Confirm that we can switch this out, instead of retrieving the complete variable.
# Original getSofttype(getVariable(dfg,lbl), solvekey)
getSofttype(v::DFGVariable) = typeof(v).parameters[1]() |
FIY, I don't know if the introspection is the best way in: Edit: added the brackets, the 2 functions are equivalent. This is just to show a cleaner way to write the same function. DF edit -- agree it's cleaner, sorry I misunderstood how |
I wanted the same concept in the summary graphs and basically did it with a warning: |
that would be a hard type -- that's an even bigger discussion. Going softtype allows a bit more freedom and does not require enumeration of all the factor permutations. EDIT
|
This issue is closely related to the possible future use of a 'manifold type'. I don't quite understand the whole hard-type soft-type thing yet, but that's beside the point. I can see how
So is the core of the issue:
Split Data Proposalssome options off the top of my head:
In the visualization use case, I needed the type to visualize it. There are only so many options that can currently be visualised. I only wanted Gaussian with a point, so PPE, but its useless without the softtype to tell you what is going on. With "summary graph", |
See edit above in the comment; to make reason a bit clearer and fix brackets. @dehann, I don't know if I understand your comment correctly, maybe elaborate if it's still applicable after the edit? |
@GearsAD if there are not too many, perhaps this idea could work for the short term. The union is not the best and just to illustrate the idea. getSofttype(::DFGVariable{T}) where T <: Union{"all the singleton types"} = T()
getSofttype(::DFGVariable{T}) where T <: Union{"all the rest"} = ...as it was before... |
Hi, trying to simplify and keep short issue -- see summary in first comment edit: #783 (comment)
If I understood you right, here is my comment update: #783 (comment)
I added my vote in first comment, and edited the Johan's suggestion above to add my support for which way forward. |
Right, so this is a more explicit version of the same idea, although in this case we'd be using the singleton form of Pose2? That sounds like a reasonable way to enforce that it doesn't retain state. |
As in the edits in the initial description:
|
if we use the inheritance approach Johan suggests then we force the user to keep type safety (if I'm understanding the use right). I was trying to do the same thing by using softtype originally, but now we need to do more things with it -- so this is a feature expansion process actually. type stability is a major performance thing, so we do need a reasonable approach to keeping that for normal use. An intermediate user should be able to augment their own data (like the radar images) and still have type safety. I think if a new user is just trying something, then combo of slow performance and documentation should help them advance towards an intermediate user (i.e. using user type for cached data).
That goes back to |
Currently we're proposing smalldata is like Union{Int, Float64, String, Vector{Int}, Vector{Float64, Vector{String}}. I think that should be a reasonable amount of flexibility and won't hammer performance? |
Oh, that will hammer performance unfortunately, the object containing a field EDIT: functions dispatching on a parameter |
Slightly off topic: This will perform way better than a "type stable" string that has to be parsed every time. If you limit the instability with other techniques such as adding type annotations and/or breaking up functions, it may be a good trade-off. For example: julia> d = Dict{Symbol, Any}();
julia> push!(d, :a=>5);
julia> push!(d, :b=>5.0)
Dict{Symbol,Any} with 2 entries:
:a => 5
:b => 5.0
julia> function sumD(d)
return d[:a]::Int + d[:b]::Float64
end
sumD (generic function with 1 method)
julia> @code_warntype sumD(d)
Variables
#self#::Core.Compiler.Const(sumD, false)
d::Dict{Symbol,Any}
Body::Float64
1 ─ %1 = Base.getindex(d, :a)::Any
│ %2 = Core.typeassert(%1, Main.Int)::Int64
│ %3 = Base.getindex(d, :b)::Any
│ %4 = Core.typeassert(%3, Main.Float64)::Float64
│ %5 = (%2 + %4)::Float64
└── return %5 |
The reason to rather use a singleton is it can only have one instance. eg julia> Pose2() === Pose2()
true
Currently, |
Added advantage, micro performance improvement. It might be negligible but this way the constant propagation can be used: #the 2 versions of:
@code_lowered getDims(p3)
# old
CodeInfo(
1 ─ %1 = Base.getproperty(p, :dims)
└── return %1
)
# new
CodeInfo(
1 ─ return 6
) |
nice! |
Decision for #784 made, consolidating work effort in this issue. |
Partially addressed by #823 - with full variables. |
Stared the deprecation process in #841. |
Too big a change to also include in v0.17.0, punting down one to v0.18.0 since this will require a breaking change upstream from DFG v0.11.0 which is not available yet. |
xref #825 |
Issue Summary
History:
variableType
was added to DFGVariable DataLevel2 to solve two problems, then DFGVariableSummary (DataLevel1) came along and is exposing two competing needs which are being wrestled out assofttype
softtypename
.Requirements
FactorMetadata
that exposes the softtype and other information to the solver.Smalldata
is an ongoing discussion for which the design is still in flux, and might induce serious performance problems owing to risk of user adding Unstable Types into the deep-inner-computation-loops.DynPose2
need to store microsecond time to allow velocity calculation, which was only added as full timestamp much later -- however, the situation can repeat with some other user data that cannot be designed in advance.Related Issues
softtypename
: wassoftypename::Symbol
a bad idea? DistributedFactorGraphs.jl#237Plan of Action
Can split these into more issues once a design decision is made.
softtype::T
should have stateful information or where to offload that requirement?use "inheritance"/"interface"/"traits" from a singleton type like Pose2 that you "inherit" and add own data to
getSofttype
should work.FactorMetadata
softtype
to onlyVariableType
see Deprecation, rename softtype -> VariableType DistributedFactorGraphs.jl#603Original Question
We need to fix all softtypes to have a default constructors, and take out all state information.
Types with issues:
DF EDIT, a related issue is how to make it easy for the user to add their own data types to the default factors. Softtype with state solved that problem, but making it a manifest or hardtype removes that option.
SC: I suggest we add smallData to factors.
The text was updated successfully, but these errors were encountered: