Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/actionscript-3/7.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Actionscript 3 大数字作为字典中的键(ActionScript 3)_Actionscript 3_Dictionary - Fatal编程技术网

Actionscript 3 大数字作为字典中的键(ActionScript 3)

Actionscript 3 大数字作为字典中的键(ActionScript 3),actionscript-3,dictionary,Actionscript 3,Dictionary,我使用的是一个键是对象的函数,但是如果键是大整数,我会遇到意想不到的问题 下面是在字典中插入两个键值对的示例代码,一个带有小键值,另一个带有大键值: var dictionary:Dictionary = new Dictionary(); var smallNumberKey:Number = 1; dictionary[smallNumberKey] = "some value"; var largeNumberKey:Number = 0x10000000; dictionary[la

我使用的是一个键是对象的函数,但是如果键是大整数,我会遇到意想不到的问题

下面是在字典中插入两个键值对的示例代码,一个带有小键值,另一个带有大键值:

var dictionary:Dictionary = new Dictionary();

var smallNumberKey:Number = 1;
dictionary[smallNumberKey] = "some value";

var largeNumberKey:Number = 0x10000000;
dictionary[largeNumberKey] = "some value";

for (var key:Object in dictionary) {
    trace("Key: " + key);
    trace("Key type: " + flash.utils.getQualifiedClassName(key));
    trace("Key as Number: " + (key as Number));
}
这将提供以下输出:

Key: 1
Key type: int
Key as Number: 1
Key: 268435456
Key type: String
Key as Number: null
似乎没有一个密钥存储为数字。为什么呢?第一个存储为int,可以转换为数字。然而,第二个似乎存储为字符串,这对我来说毫无意义。这是怎么回事?

来自Adobe文档:

Dictionary类允许您创建属性的动态集合,该集合使用严格相等(==)进行键比较。当一个对象用作键时,该对象的标识用于查找该对象,而不是对其调用toString()返回的值

“使用对象的标识”意味着使用对对象的引用,即指向实际对象存储在内存中的位置的指针。将基元值用作字典键时的问题是,它们永远不会通过引用传递,因此这些值不会存储在实际字典中(即,它们不是对对象的引用),而是被视为“常规”动态属性,就像您期望从
对象
获得的属性一样。当你设定

object[key] = "some value";
键值会自动转换为
int
(就像
数组的索引一样)或
字符串

通过使用一个简单的
NumberKey
包装类,您可以绕过此问题,并利用
字典
的实际性能优势:

package
{
    import flash.display.Sprite;
    import flash.utils.Dictionary;


    public class SimpleTest extends Sprite
    {
        var dictionary:Dictionary = new Dictionary();

        public function SimpleTest() {
            var smallNumberKey:NumberKey = new NumberKey(1);
            dictionary[smallNumberKey] = "some value";

            var largeNumberKey:NumberKey = new NumberKey(0x10000000);
            dictionary[largeNumberKey] = "some value";

            for(var key:Object in dictionary) {
                trace( "Key: "+key );
                trace( "Key type: "+flash.utils.getQualifiedClassName( key ) );
                trace( "Key as Number: "+(key.numberValue) );
            }
        }
    }
}

package {
    public class NumberKey {
        public var numberValue : Number;

        public function NumberKey( n:Number ) {
            numberValue = n;
        }
    }
}

不能使用
数字
作为键,因为二进制浮点数不适合进行精确比较,这正是
字典
类所做的。(是“使用严格相等(==)进行键比较”)。阅读浮点数,了解原因

因此,当您将一个
数字
指定为
字典
的键时,Flash引擎必须将其转换为可以精确表示的其他内容
String
int
值都可以由它们的内容精确表示,因此Flash选择一个值来将提供的
数字转换为。在进行一些实验时,flash似乎总是将小于或等于0xFFFFFFF的整数值(即使作为字符串提供)转换为
int
,并且总是将大于该值的任何整数转换为
string
,这可能是由于一些内部优化以最快的方式比较键:

import flash.utils.Dictionary;
import flash.utils.getQualifiedClassName;

var dictionary:Dictionary = new Dictionary();
var stringKey:String = "123456789";
var intKey:int = 0xFFFFFFF;
var intKey2:int = intKey + 1;

dictionary[stringKey] = "Value 1";
dictionary[intKey] = "Value 2";
dictionary[intKey2] = "Value 3";

for (var key:Object in dictionary) {
    trace( key + " [" + getQualifiedClassName(key) + "] = " + dictionary[key]);
}
印刷品:

123456789 [int] = Value 1
268435455 [int] = Value 2
268435456 [String] = Value 3

对这种方法要非常小心。由于您使用的是对象,因此提供给
NumberKey
Number
与键作为
字典
键的身份无关。用完全相同的数字构造一百万个
NumberKey
对象将创建一百万个唯一的字典条目。当然,这是正确的。您需要跟踪已创建的关键点。但这是实际使用Dictionary的Dictionary部分的唯一方法。使用原语值作为键可以为Dictionary实例添加动态属性,但它没有利用Dictionary的优化机制。如果采用这种方法,还可以使用一个简单的对象。