M
Marcus Kwok
I wrote a little test program to demonstrate what may be a
misunderstanding on my part in the behavior of ArrayList::Sort().
I defined a class (Test) that has two data members: a System::String*
(name) and a double value. Test implements IComparable, so I made the
CompareTo() function sort first by name, then by the value of the
double.
When I run the code below, it sorts by name correctly, but it does not
sort correctly the items with the same name.
#using <mscorlib.dll>
using namespace System;
using namespace System::Collections;
public __gc class Test : public IComparable {
public:
Test(System::String* name, double d)
: name_(name)
, d_(d)
{ }
Int32 CompareTo(Object* obj)
{
if (obj->GetType() == __typeof(Test)) {
Test* t = dynamic_cast<Test*>(obj);
return (name_->Equals(t->name_) ? d_ < t->d_ : name_->CompareTo(t->name_));
}
throw new ArgumentException("object is not a Test");
}
System::String* ToString()
{
return String::Concat(name_, S": ", __box(d_));
}
private:
System::String* name_;
double d_;
};
int main()
{
ArrayList* array = new ArrayList;
array->Add(new Test(S"Me", 1.0));
array->Add(new Test(S"A", 0.0));
array->Add(new Test(S"Me", 2.0));
array->Add(new Test(S"B", 0.0));
array->Add(new Test(S"Me", 3.0));
array->Add(new Test(S"C", 0.0));
array->Add(new Test(S"Me", 4.0));
Console::WriteLine(S"Original:");
for (int i = 0; i < array->Count; ++i) {
Console::WriteLine(array->Item);
}
Console::WriteLine();
for (int i = 0; i < 4; ++i) {
array->Sort();
Console::WriteLine(String::Concat(S"After Sort() #", __box(i + 1)->ToString(), ":"));
for (int i = 0; i < array->Count; ++i) {
Console::WriteLine(array->Item);
}
Console::WriteLine();
}
return 0;
}
Output:
Original:
Me: 1
A: 0
Me: 2
B: 0
Me: 3
C: 0
Me: 4
After Sort() #1:
A: 0
B: 0
C: 0
Me: 4
Me: 3
Me: 2
Me: 1
After Sort() #2:
A: 0
B: 0
C: 0
Me: 2
Me: 1
Me: 4
Me: 3
After Sort() #3:
A: 0
B: 0
C: 0
Me: 4
Me: 3
Me: 2
Me: 1
After Sort() #4:
A: 0
B: 0
C: 0
Me: 2
Me: 1
Me: 4
Me: 3
misunderstanding on my part in the behavior of ArrayList::Sort().
I defined a class (Test) that has two data members: a System::String*
(name) and a double value. Test implements IComparable, so I made the
CompareTo() function sort first by name, then by the value of the
double.
When I run the code below, it sorts by name correctly, but it does not
sort correctly the items with the same name.
#using <mscorlib.dll>
using namespace System;
using namespace System::Collections;
public __gc class Test : public IComparable {
public:
Test(System::String* name, double d)
: name_(name)
, d_(d)
{ }
Int32 CompareTo(Object* obj)
{
if (obj->GetType() == __typeof(Test)) {
Test* t = dynamic_cast<Test*>(obj);
return (name_->Equals(t->name_) ? d_ < t->d_ : name_->CompareTo(t->name_));
}
throw new ArgumentException("object is not a Test");
}
System::String* ToString()
{
return String::Concat(name_, S": ", __box(d_));
}
private:
System::String* name_;
double d_;
};
int main()
{
ArrayList* array = new ArrayList;
array->Add(new Test(S"Me", 1.0));
array->Add(new Test(S"A", 0.0));
array->Add(new Test(S"Me", 2.0));
array->Add(new Test(S"B", 0.0));
array->Add(new Test(S"Me", 3.0));
array->Add(new Test(S"C", 0.0));
array->Add(new Test(S"Me", 4.0));
Console::WriteLine(S"Original:");
for (int i = 0; i < array->Count; ++i) {
Console::WriteLine(array->Item);
}
Console::WriteLine();
for (int i = 0; i < 4; ++i) {
array->Sort();
Console::WriteLine(String::Concat(S"After Sort() #", __box(i + 1)->ToString(), ":"));
for (int i = 0; i < array->Count; ++i) {
Console::WriteLine(array->Item);
}
Console::WriteLine();
}
return 0;
}
Output:
Original:
Me: 1
A: 0
Me: 2
B: 0
Me: 3
C: 0
Me: 4
After Sort() #1:
A: 0
B: 0
C: 0
Me: 4
Me: 3
Me: 2
Me: 1
After Sort() #2:
A: 0
B: 0
C: 0
Me: 2
Me: 1
Me: 4
Me: 3
After Sort() #3:
A: 0
B: 0
C: 0
Me: 4
Me: 3
Me: 2
Me: 1
After Sort() #4:
A: 0
B: 0
C: 0
Me: 2
Me: 1
Me: 4
Me: 3