From e045162db4b92deb317f5324bd9b4dda7af3172b Mon Sep 17 00:00:00 2001 From: Johannes Terblanche Date: Thu, 13 Aug 2020 16:40:00 +0200 Subject: [PATCH] Save/load module with softtype --- src/services/Serialization.jl | 46 ++++++++++++++++++++++++++--------- 1 file changed, 34 insertions(+), 12 deletions(-) diff --git a/src/services/Serialization.jl b/src/services/Serialization.jl index 93ffc138..c049ff23 100644 --- a/src/services/Serialization.jl +++ b/src/services/Serialization.jl @@ -10,6 +10,34 @@ import JSON.Serializations: CommonSerialization, StandardSerialization JSON.show_json(io::JSONContext, serialization::CommonSerialization, uuid::UUID) = print(io.io, "\"$uuid\"") +function typeModuleName(softtype::InferenceVariable) + io = IOBuffer() + ioc = IOContext(io, :module=>DistributedFactorGraphs) + show(ioc, typeof(softtype)) + return String(take!(io)) +end + +function getTypeFromSerializationModule(softtypeString::String) + try + # split the type at last `.` + split_st = split(softtypeString, r"\.(?!.*\.)") + #if module is specified look for the module in main, otherwise use Main + if length(split_st) == 2 + m = getfield(Main, Symbol(split_st[1])) + else + m = Main + end + return getfield(m, Symbol(split_st[end])) + + catch ex + @error "Unable to deserialize soft type $(softtypeString)" + io = IOBuffer() + showerror(io, ex, catch_backtrace()) + err = String(take!(io)) + @error(err) + end + nothing +end ##============================================================================== ## Variable Packing and unpacking ##============================================================================== @@ -23,9 +51,7 @@ function packVariable(dfg::G, v::DFGVariable)::Dict{String, Any} where G <: Abst props["solverDataDict"] = JSON2.write(Dict(keys(v.solverDataDict) .=> map(vnd -> packVariableNodeData(dfg, vnd), values(v.solverDataDict)))) props["smallData"] = JSON2.write(v.smallData) props["solvable"] = v.solvable - props["softtype"] = string(typeof(getSofttype(v))) - # props["bigData"] = JSON2.write(Dict(keys(v.dataDict) .=> map(bde -> JSON2.write(bde), values(v.dataDict)))) - # props["bigDataElemType"] = JSON2.write(Dict(keys(v.dataDict) .=> map(bde -> typeof(bde), values(v.dataDict)))) + props["softtype"] = typeModuleName(getSofttype(v)) props["dataEntry"] = JSON2.write(Dict(keys(v.dataDict) .=> map(bde -> JSON.json(bde), values(v.dataDict)))) props["dataEntryType"] = JSON2.write(Dict(keys(v.dataDict) .=> map(bde -> typeof(bde), values(v.dataDict)))) @@ -88,8 +114,8 @@ function unpackVariable(dfg::G, smallData = JSON2.read(packedProps["smallData"], Dict{Symbol, SmallDataTypes}) softtypeString = packedProps["softtype"] - softtype = getTypeFromSerializationModule(dfg, Symbol(softtypeString)) - softtype == nothing && error("Cannot deserialize softtype '$softtypeString' in variable '$label'") + softtype = getTypeFromSerializationModule(softtypeString) + isnothing(softtype) && error("Cannot deserialize softtype '$softtypeString' in variable '$label'") if unpackSolverData packed = JSON2.read(packedProps["solverDataDict"], Dict{String, PackedVariableNodeData}) @@ -139,7 +165,7 @@ function packVariableNodeData(dfg::G, d::VariableNodeData)::PackedVariableNodeDa d.BayesNetOutVertIDs, d.dimIDs, d.dims, d.eliminated, d.BayesNetVertID, d.separator, - d.softtype != nothing ? string(d.softtype) : nothing, + typeModuleName(d.softtype), d.initialized, d.inferdim, d.ismargin, @@ -158,14 +184,10 @@ function unpackVariableNodeData(dfg::G, d::PackedVariableNodeData)::VariableNode c4 = r4 > 0 ? floor(Int,length(d.vecbw)/r4) : 0 M4 = reshape(d.vecbw,r4,c4) - # TODO -- allow out of module type allocation (future feature, not currently in use) @debug "Dispatching conversion packed variable -> variable for type $(string(d.softtype))" # Figuring out the softtype - unpackedTypeName = split(d.softtype, "(")[1] - unpackedTypeName = split(unpackedTypeName, '.')[end] - @debug "DECODING Softtype = $unpackedTypeName" - st = getTypeFromSerializationModule(dfg, Symbol(unpackedTypeName)) - st == nothing && error("The variable doesn't seem to have a softtype. It needs to set up with an InferenceVariable from IIF. This will happen if you use DFG to add serialized variables directly and try use them. Please use IncrementalInference.addVariable().") + st = getTypeFromSerializationModule(d.softtype) + isnothing(st) && error("The variable doesn't seem to have a softtype. It needs to set up with an InferenceVariable from IIF. This will happen if you use DFG to add serialized variables directly and try use them. Please use IncrementalInference.addVariable().") return VariableNodeData{st}(M3,M4, d.BayesNetOutVertIDs, d.dimIDs, d.dims, d.eliminated, d.BayesNetVertID, d.separator,