c# - Custom string class equality -
i'm making custom string class. (mainly self-edification purposes - know i'm not going come better regular string
class couldn't extension methods.) i'm running weird problem testing equality in unit tests. works in every respect except one. here's unit tests:
mystring mystr = "mynewstring"; assert.areequal("mynewstring", mystr); //fails assert.areequal(mystr, "mynewstring"); assert.istrue(mystr.equals("mynewstring")); assert.istrue(("mynewstring").equals(mystr)); assert.istrue(mystr == "mynewstring"); assert.istrue("mynewstring" == mystr); string realstring = "mynewstring"; assert.areequal(realstring, mystr); //fails assert.areequal(mystr, realstring); assert.istrue(mystr.equals(realstring)); assert.istrue(realstring.equals(mystr)); assert.istrue(mystr == realstring); assert.istrue(realstring == mystr);
in both cases fails, succeed if add .tostring()
after mystr
, not required in of other cases. i'm guessing it's because string
's equals
methods don't know class, though i've got implicit conversions set up. relevant parts of class follows:
public struct mystring : icloneable, icomparable<mystring>, icomparable<string>, ienumerable<char>, iequatable<mystring>, iequatable<string> { private char[] text; //constructors ... public static implicit operator mystring(string s) { return s == null ? null : new mystring(s); } public static implicit operator string(mystring s) { return s.tostring(); } public static bool operator ==(mystring a, mystring b) { return a.equals(b); } public static bool operator !=(mystring a, mystring b) { return !(a.equals(b)); } public static bool operator ==(mystring a, string b) { return a.equals(b); } public static bool operator !=(mystring a, string b) { return !(a.equals(b)); } public static bool operator ==(string a, mystring b) { return b.equals(a); } public static bool operator !=(string a, mystring b) { return !(b.equals(a)); } public override string tostring() { return new string(text); } public override bool equals(object obj) { if (obj == null) return false; if (base.equals(obj)) return true; if (obj mystring) return this.equals((mystring)obj); if (obj string) return this.equals((string)obj); return false; } public bool equals(mystring other) { return this.compareto(other) == 0; } public bool equals(string other) { return this.compareto(other) == 0; } }
there's compareto()
's both mystring
, regular string
, trust me work. there else can make equality test work? seems work in every other case one. i'm not sure how assert.areequal
operates internally, if every other method testing equality works, why 1 fail?
edit: adding gethashcode() might relevant:
public override int gethashcode() { int hash = 0; (int = 0; < length; i++ ) hash ^= (i * this[i]); return hash; }
for sure doesn't match string.gethashcode()
, have no way of knowing because can't see code. (i can see metadata, includes headers , not implementation.) tried replacing shortcut string.gethashcode()
:
public override int gethashcode() { return new string(text).gethashcode(); }
still doesn't work. tried adding extension method:
public static bool equals(this string a, mystring b) { return b.equals(a); }
that didn't work either. other ideas?
the call stack mentions call of assert.areequal(object, object)
assume call object.equals(object, object)
not call of operators. see http://blogs.msdn.com/b/csharpfaq/archive/2004/03/29/when-should-i-use-and-when-should-i-use-equals.aspx
btw: please sure overwrite gethashcode()
i had extend little bit.
assert.areequal(a,b)
calls object.equals(a,b)
calls a.equals(b)
. test calls string.equals(b)
. implementation of string.equals
implicit cast string referenceequalscomparism. so, long no implicit cast string exists, string.equality() fail.
in short: implicit cast mystring string not work => see in c# 3.0, possible add implicit operators string class?
var mystr = "hello" mystring; // call implicit cast mystring var y = mystr string; // not call implicit cast string becaus not owner of string
Comments
Post a Comment