Использование объектов в качестве ключей карты в Haxe

Я пытаюсь сделать Map с объектом в качестве ключа. Проблема в том, что когда я пытаюсь получить элементы с этой карты, я всегда получаю null. Это потому, что я не даю ту же ссылку, что и ключ. Я предоставляю объекту те же значения, поэтому ссылка будет другой.

Есть ли способ решить эту проблему? Могу я заставить его использовать какую-нибудь equals() функцию?

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)

person Krzycho    schedule 09.12.2014    source источник


Ответы (1)


Как объяснено здесь и здесь, Map в Haxe работает, используя ссылку на объект в качестве ключа.

Вместо этого вы хотите использовать HashMap, подобный этому (ссылка try.haxe):

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)';
    }
}

Что вам нужно изменить в вашем коде, помимо использования haxe.ds.HashMap вместо Map, так это реализовать функцию hashCode : Void->Int в вашем ключевом объекте.

Поскольку вы используете объект с двумя целыми числами, а хеш-карта - это всего лишь одно целое, может случиться так, что 2 PointInt будут иметь одинаковый хэш-код. Чтобы решить эту проблему, вы можете создать хэш-карту, которая использует строки в качестве хэш-кода, но если вы можете написать (или погуглить) хорошую хеш-функцию, вы получите лучшую производительность.

person npretto    schedule 09.12.2014
comment
Итак, что я сделал сейчас, изменил ObjectMap ‹PointInt, Hex› на ObjectMap ‹String, Hex›. Я сделал простую функцию хеширования для строки в классе PointInt. Это медленно, но делает то, что нужно. Может быть, когда-нибудь появятся другие варианты. знак равно - person Krzycho; 09.12.2014
comment
Возможно ли, что функция hashCode требуется для получения уникальных результатов для разных объектов? try.haxe.org/#B753E Насколько я понимаю, HashMap должен использовать функцию hashCode для сегментирования , но не для различения предметов. - person brdlph; 20.05.2015