Javascript noob-创建一个;“设置”;类,代码不工作

Javascript noob-创建一个;“设置”;类,代码不工作,javascript,class,set,Javascript,Class,Set,我有以下代码(实际上是创建一个Set类,或者更明确地说是创建一个无序的值集合,没有重复项) 不幸的是,它不起作用==>在调试器中运行它时,我看到以下行返回“undefined”: o[prop]=Set._v2s.next++ 我认为这是因为o=“o”,所以我不能使用这个带字符串的Set类 您知道如何修改代码,以便我可以将其与字符串一起使用(如我所附的示例中所示)吗 代码如下: function Set(){ // the constructor this.values = {}; /

我有以下代码(实际上是创建一个Set类,或者更明确地说是创建一个无序的值集合,没有重复项)

不幸的是,它不起作用==>在调试器中运行它时,我看到以下行返回“undefined”: o[prop]=Set._v2s.next++

我认为这是因为o=“o”,所以我不能使用这个带字符串的Set类

您知道如何修改代码,以便我可以将其与字符串一起使用(如我所附的示例中所示)吗

代码如下:

function Set(){ // the constructor
     this.values = {}; // an empty object that will keep all the set elements' 
                       // names as properties 
     this.n = 0; // #values in the set
     this.add.apply(this, arguments); // when initially build the set then add all     the   arguments of the constructor into the set
}



// Add each of the arguments of the constructor to the set
Set.prototype.add = function(){
    for (var i=0; i<arguments.length; i++){ // for each argument of the constructor
        var val = arguments[i];
        var str = Set._v2s(val); // transform the value to a string
        if (!this.values.hasOwnProperty(str)){ // If not already in the set
            this.values[str]=val; // Load the element in the set
            this.n++;   
            }
        }
    return this; // support chained method call
};



// Remove each of the arguments  from the set
Set.prototype.remove = function(){
     for (var i=0; i<arguments.length; i++){ // for each argument
        var str = Set._v2s(arguments[i]);
        if (this.values.hasOwnProperty(str)){ // If the element is in the set already
        delete this.values[str];
        this.n--;   // Delete it
        }
    }
    return this;
};



// Return true if the set contains a value; false otherwise
Set.prototype.contains = function(value){
    return this.values.hasOwnProperty(Set._v2s(value));
};

// Return the size of the set
Set.prototype.size = function(){
    return this.n;
};

// Call function f on the specified context for each element of the set.
Set.prototype.foreach = function(f,context){
    for (var s in this.values)
        if (this.values.hasOwnProperty(s)) // ignore inherited props
             f.call(context,this.values[s]);    // call f on the value
};

// This internal function maps any JavaScript value to a unique string.
Set._v2s = function(val){
    switch (val){
        case undefined: return 'u'; // special primitive
            case null: return 'n';
            case true: return 't';
            case false: return 'f';
            default: switch(typeof val){
                case 'number': return '#' + val;    // numbers get the # prefix
                case 'string': return '@' + objectId(val);
            }
        }
};      
    // for any object, return a string ( a unique one per object, and if applied repeatedly on the same object will return the same string. The key technique is to add a (nonenumerable and read-only in ES5) property to object o.
    function objectId(o){
        var prop = "|**objectid**|"; // private property name for storing ids
        if (!o.hasOwnProperty(prop)) // if the object has no id
            o[prop] = Set._v2s.next++; // assign it the next available
            return o[prop];
};  

Set._v2s.next = 100;    // start assigning objectids at this value.     

var my_set = new Set("o","pojo");
alert(my_set.size);
function Set(){//构造函数
this.values={};//将保留所有集合元素的空对象
//名称作为属性
此.n=0;//#集合中的值
this.add.apply(this,arguments);//最初构建集合时,将构造函数的所有参数添加到集合中
}
//将构造函数的每个参数添加到集合中
Set.prototype.add=函数(){

对于(var i=0;i嗯,通过运行您的代码,我发现了一个小错误
alert(my_set.size);
在定义中,
Set.prototype.size=function(){
归还这个;
};
因此,size是一个方法,所以您应该将其称为method以返回正确的结果,例如
var result=my_set.size()

显然,您无法为JS中的原语分配新属性。这样如何:

var objectId = (function() {
  var next = 100; // start assigning objectids at this value.     
  var ids = {};
  return function(o){
    if (!ids.hasOwnProperty(o)) // if the object has no id
        ids[o] = next++; // assign it the next available
    return ids[o];
  };  
}) ();

为什么要将值映射到字符串?很抱歉,这不是我在JS中所说的有用对象,特别是因为现在,您可以简单地执行
object.keys(setInstance).length;
,这可能比您尝试执行的操作更便宜…您还可以扩充该函数实例:
Set.prototype.size.valueOf=Set.prototype.size.toString=function(){return this();};