Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using objects as Map keys in Haxe

Tags:

haxe

I'm trying to make a Map with an object as a key. The problem is, that when I try to get elements from this map, I always get null. It's because I'm not providing the exact same reference as the key was. I'm providing an object with the same values, so the reference is different.

Is there any way to solve that? Can I make it use some kind of equals() function?

class PointInt
{
    public var x:Int;
    public var y:Int;

    ...
}
var map = new Map<PointInt, Hex>();

var a = new PointInt(1, 1);
var b = new PointInt(1, 1);

var hex_a = new Hex();

map[a] = hex_a;
var hex_b = map[b];

/// hex_b == null now because reference(a) == reference(b)
like image 972
Krzycho Avatar asked Oct 17 '25 17:10

Krzycho


1 Answers

As explained here and here, Map in Haxe works using the reference of the object as the key.

What you want to use instead is a HashMap like this (try.haxe link):

import haxe.ds.HashMap;

class Test {
    static function main() {

        var map = new HashMap();
        map.set(new PointInt(1, 1), 1);

        trace(map.get(new PointInt(1,1)));
    }
}

class PointInt
{
    public var x:Int;
    public var y:Int;

    public function new(x:Int, y:Int)
    {
        this.x = x;
        this.y = y;
    }

    public function hashCode():Int
    {
        return x + 1000*y; //of course don't use this, but a real hashing function
    }

    public function toString()
    {
        return '($x,$y)';
    }
}

What you need to change in your code, besides using haxe.ds.HashMap instead of Map is to implement a hashCode : Void->Int function in your key object

Since you're using an object that has 2 ints, and the hash map is just 1 int, it will happen that 2 PointInt will have the same hash code. To solve this you could create a hash map that uses strings as hashcode but if you can write (or google) a good hash function you will get better performance.

like image 114
npretto Avatar answered Oct 22 '25 07:10

npretto