Question

I need to assign a guid to objects for managing state at app startup & shutdown It looks like i can store the lookup values in a dictionary using

dictionary<int,Guid>.Add(instance.GetHashCode(), myGUID());

are there any potential issues to be aware of here ?

NOTE

This does NOT need to persist between execution runs, only the guid like so

  • create the object
  • gethashcode(), associate with new or old guid
  • before app terminate, gethashcode() and lookup guid to update() or insert() into persistence engine USING GUID

    only assumption is that the gethashcode() remains consistent while the process is running

    also gethashcode() is called on the same object type (derived from window)

Update 2 - here is the bigger picture

  • create a state machine to store info about WPF user controls (later ref as UC) between runs
  • the types of user controls can change over time (added / removed)
  • in the very 1st run, there is no prior state, the user interacts with a subset of UC and modifies their state, which needs to recreated when the app restarts
  • this state snapshot is taken when the app has a normal shutdown
  • also there can be multiple instances of a UC type
  • at shutdown, each instance is assigned a guid and saved along with the type info and the state info
  • all these guids are also stored in a collection
  • at restart, for each guid, create object, store ref/guid, restore state per instance so the app looks exactly as before
  • the user may add or remove UC instances/types and otherwise interact with the system
  • at shutdown, the state is saved again
  • choices at this time are to remove / delete all prior state and insert new state info to the persistence layer (sql db)
  • with observation/analysis over time, it turns out that a lot of instances remain consistent/static and do not change - so their state need not be deleted/inserted again as the state info is now quite large and stored over a non local db
  • so only the change delta is persisted
  • to compute the delta, need to track reference lifetimes
  • currently stored as List<WeakReference> at startup
  • on shutdown, iterate through this list and actual UC present on screen, add / update / delete keys accordingly
  • send delta over to persistence

Hope the above makes it clear.

So now the question is - why not just store the HashCode (of usercontrol only) instead of WeakReference and eliminate the test for null reference while iterating thru the list

update 3 - thanks all, going to use weakreference finally

Was it helpful?

Solution

Use GetHashCode to balance a hash table. That's what it's for. Do not use it for some other purpose that it was not designed for; that's very dangerous.

OTHER TIPS

You appear to be assuming that a hash code will be unique. Hash codes don't work like that. See Eric Lippert's blog post on Guidelines and rules for GetHashCode for more details, but basically you should only ever make the assumptions which are guaranteed for well-behaving types - namely the if two objects have different hash codes, they're definitely unequal. If they have the same hash code, they may be equal, but may not be.

EDIT: As noted, you also shouldn't persist hash codes between execution runs. There's no guarantee they'll be stable in the face of restarts. It's not really clear exactly what you're doing, but it doesn't sound like a good idea.

EDIT: Okay, you've now noted that it won't be persistent, so that's a good start - but you still haven't dealt with the possibility of hash code collisions. Why do you want to call GetHashCode() at all? Why not just add the reference to the dictionary?

The quick and easy fix seems to be

var dict = new Dictionary<InstanceType, Guid>();
dict.Add(instance, myGUID());

Of course you need to implement InstanceType.Equals correctly if it isn't yet. (Or implement IEQuatable<InstanceType>)

Possible issues I can think of:

  • Hash code collisions could give you duplicate dictionary keys
  • Different object's hash algorithms could give you the same hash code for two functionally different objects; you wouldn't know which object you're working with
  • This implementation is prone to ambiguity (as described above); you may need to store more information about your objects than just their hash codes.

Note - Jon said this more elegantly (see above)

Since this is for WPF controls, why not just add the Guid as a dependency proptery? You seem to already be iterating through the user controls, in order to get their hash codes, so this would probably be a simpler method.

If you want to capture that a control was removed and which Guid it had, some manager object that subscribes to closing/removed events and just store the Guid and a few other details would be a good idea. Then you would also have an easier time to capture more details for analysis if you need.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top