Node Get(ref object key) { if (key is double) { double kd = (double)key; int k = (int)kd; if ((double)k == kd) /* is an integer index? */ { return(GetInt(k)); /* use specialized version */ } else { return(GetDouble(kd)); } } else if (key is Symbol) { return(GetSymbol((Symbol)key)); } else if (key is String) { Symbol s = Symbol.Intern(((String)key).S); key = s; return(GetSymbol(s)); } else { return(GetAny(key)); } }
int Hash(object o) { if (o is double) { return(Hash((double)o)); } else if (o is Symbol) { return(Hash((Symbol)o)); } else if (o is String) { return(Hash(Symbol.Intern(((String)o).S))); } else { return(o.GetHashCode() % ((this.node.Length - 1) | 1)); } }
public override object this[object index] { get { object value = Nil.Instance; if (index is Symbol) { Symbol key = (Symbol)index; Node n = this.node[key.hash % ((this.node.Length - 1) | 1)]; do /* check whether `key' is somewhere in the chain */ { if (key == n.key) { value = n.val; break; /* that's it */ } else { n = n.next; } } while (n != null); } else if (index is double) { double kd = (double)index; int k = (int)kd; if ((double)k == kd) /* is an integer index? */ { value = GetInt(k).val; /* use specialized version */ } else { value = GetDouble(kd).val; } } else if (index is String) { Symbol key = Symbol.Intern(((String)index).S); Node n = this.node[key.hash % ((this.node.Length - 1) | 1)]; do /* check whether `key' is somewhere in the chain */ { if (key == n.key) { value = n.val; /* that's it */ break; } else { n = n.next; } } while (n != null); } else { value = GetAny(index).val; } object idx_meta; if (value == Nil.Instance && this._meta != null && ((idx_meta = this._meta.GetSymbol(Reference.__index).val) != Nil.Instance)) { if (idx_meta is Closure) { value = ((Reference)idx_meta).InvokeS(this, index); } else { value = ((Table)idx_meta)[index]; } } return(value); } set { Node p = Get(ref index); if (p != Node.NilNode) { p.val = value; } else if (value != Nil.Instance) { if (index == Nil.Instance) { throw new Exception("table index is nil"); } p = NewKey(index); p.val = value; } } }