Сравнить два Object
От: Аноним  
Дата: 21.09.09 06:30
Оценка:
Привет всем.

Народ есть два объекта записанные в Object. Какой тип там сохранен не известно.
Известно, что только типы совпадают и для них определены операторы сравнения. (int, float, double, String и т.д.)
Как их сравнить на равно, не равно понятно.
Возможно ли придумать механизм сравнения на больше меньше без приведения к явному типу
т.е. чтобы избежать такой записи:
if(obj1.Type() == typeof(int) )
return ((int)obj1) < ((int)obj2);

if(obj1.Type() == typeof(float) )
...
if(obj1.Type() == typeof(double) )
...
и т.д.

Заранее спасибо
Re: Сравнить два Object
От: Александр Кузнецов Россия  
Дата: 21.09.09 06:44
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Возможно ли придумать механизм сравнения на больше меньше без приведения к явному типу


Посмотри интерфейс IComparable. Получишь что-то вида:

if(obj1 is IComparable)
   return ((obj1 as IComparable).CompareTo(obj2) > 0);
"Пишите код так, как будто сопровождать его будет склонный к насилию психопат, который знает, где вы живете". (с) Макконнелл, "Совершенный код".
Re: Сравнить два Object
От: Аноним  
Дата: 21.09.09 06:52
Оценка: +1
Здравствуйте, Аноним, Вы писали:

А>
if(obj1.Type() == typeof(int) )

Руки бы поотрывать за эту строчку .

Вот как надо писать: if (obj is int)
Re[2]: Сравнить два Object
От: Аноним  
Дата: 21.09.09 06:58
Оценка:
А>Руки бы поотрывать за эту строчку .
А>Вот как надо писать: if (obj is int)

Спасибо на добром слове, но критика заслуженная.
Почему-то считал если тип non-nullable то ни as ни is с ним не работают
Спасибо
Re[2]: Сравнить два Object
От: Аноним  
Дата: 21.09.09 07:08
Оценка: 1 (1) +3
Здравствуйте, Александр Кузнецов, Вы писали:

АК>
return ((obj1 as IComparable).CompareTo(obj2) > 0);


Не (obj1 as IComparable), а ((IComparable)obj1). Инструкция as для другого предназначена.
Re: Сравнить два Object
От: _FRED_ Черногория
Дата: 21.09.09 08:01
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Народ есть два объекта записанные в Object. Какой тип там сохранен не известно.

А>Известно, что только типы совпадают и для них определены операторы сравнения. (int, float, double, String и т.д.)
А>Как их сравнить на равно, не равно понятно.
А>Возможно ли придумать механизм сравнения на больше меньше без приведения к явному типу

Раз типы совпадают, то можно
    var x = (object)0;
    var y = (object)3;
    var compare1 = Comparer<object>.Default.Compare(x, y);
    var compare2 = Comparer<object>.Default.Compare(y, x);
    Debug.Assert(compare1 == -compare2, "compare1 == -compare2");
Help will always be given at Hogwarts to those who ask for it.
Re: Сравнить два Object
От: hexamino http://hexamino.blogspot.com/
Дата: 21.09.09 08:01
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Возможно ли придумать механизм сравнения на больше меньше без приведения к явному типу


В C# 4.0 можно просто привести аргументы к типу dynamic и применить к ним обычный оператор >.
Re[2]: Сравнить два Object
От: koandrew Канада http://thingselectronic.blogspot.ca/
Дата: 21.09.09 11:38
Оценка: :)
Здравствуйте, Аноним, Вы писали:


А>Руки бы поотрывать за эту строчку .


А>Вот как надо писать: if (obj is int)


А я бы вот за ваш код руки поотрывал. Ибо применение такого подхода везде может привести к неожиданным и неприятным эффектам при использовании полиморфных иерархий классов:
if (obj is ParentClass)
{
  //
}
else if (obj is ChildClass)
{
  //
}
[КУ] оккупировала армия.
Re[2]: Сравнить два Object
От: koandrew Канада http://thingselectronic.blogspot.ca/
Дата: 21.09.09 11:39
Оценка:
Здравствуйте, hexamino, Вы писали:

H>Здравствуйте, Аноним, Вы писали:


А>>Возможно ли придумать механизм сравнения на больше меньше без приведения к явному типу


H>В C# 4.0 можно просто привести аргументы к типу dynamic и применить к ним обычный оператор >.


А в чём смысл сего действа? Избавиться от ошибки компиляции и вместо этого получить её в райтайме?
[КУ] оккупировала армия.
Re[3]: Сравнить два Object
От: hexamino http://hexamino.blogspot.com/
Дата: 21.09.09 11:50
Оценка:
Здравствуйте, koandrew, Вы писали:

H>>В C# 4.0 можно просто привести аргументы к типу dynamic и применить к ним обычный оператор >.


K>А в чём смысл сего действа? Избавиться от ошибки компиляции и вместо этого получить её в райтайме?


Смысл в том, что в рантайме вызовется оператор сравнения у соответствующего типа: int, long, double, decimal или какого-то user-defined типа. Конечно, программист должен позаботится о том, что он передает туда подходящий тип или хотя бы перехватывает исключение.
Re[3]: Сравнить два Object
От: _FRED_ Черногория
Дата: 21.09.09 12:11
Оценка:
Здравствуйте, koandrew, Вы писали:

А>>Руки бы поотрывать за эту строчку .

А>>Вот как надо писать: if (obj is int)
K>А я бы вот за ваш код руки поотрывал. Ибо применение такого подхода везде может привести к неожиданным и неприятным эффектам при использовании полиморфных иерархий классов:

Впрочем, как и любое применение произвольного правила без попытки понять его (правила) суть

В данном случае код

if (obj is int)


решает одну задачу, а код

K>if (obj is ParentClass)
K>{
K>  //
K>}
K>else if (obj is ChildClass)
K>{
K>  //
K>}


совершенно другую.
Help will always be given at Hogwarts to those who ask for it.
Re[3]: Сравнить два Object
От: nikov США http://www.linkedin.com/in/nikov
Дата: 21.09.09 12:19
Оценка:
Здравствуйте, koandrew, Вы писали:

K>Ибо применение такого подхода везде может привести к неожиданным и неприятным эффектам при использовании полиморфных иерархий классов:
if (obj is ParentClass)
K>{
K>  //
K>}
K>else if (obj is ChildClass)
K>{
K>  //
K>}
K>


Это не грозит тем, у кого стоит ReSharper.
Re: Сравнить два Object
От: Undying Россия  
Дата: 23.09.09 06:04
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Народ есть два объекта записанные в Object. Какой тип там сохранен не известно.

А>Известно, что только типы совпадают и для них определены операторы сравнения. (int, float, double, String и т.д.)
А>Как их сравнить на равно, не равно понятно.
А>Возможно ли придумать механизм сравнения на больше меньше без приведения к явному типу

Можно так:

    public static int ValueComparison(object value1, object value2)
    {
      IComparable comparable1 = value1 as IComparable;
      if (comparable1 != null)
      {
        return comparable1.CompareTo(value2);
      }
      else
      {
        IComparable comparable2 = value2 as IComparable;
        if (comparable2 != null)
        {
          return -comparable2.CompareTo(value1);
        }
      }
      return 0;
    }
Re[2]: Сравнить два Object
От: _FRED_ Черногория
Дата: 23.09.09 07:52
Оценка: 1 (1)
Здравствуйте, Undying, Вы писали:

А>>Возможно ли придумать механизм сравнения на больше меньше без приведения к явному типу

U>Можно так:
U>    public static int ValueComparison(object value1, object value2)
U>    {
U>      IComparable comparable1 = value1 as IComparable;
U>      if (comparable1 != null)
U>      {
U>        return comparable1.CompareTo(value2);
U>      }
U>      else
U>      {
U>        IComparable comparable2 = value2 as IComparable;
U>        if (comparable2 != null)
U>        {
U>          return -comparable2.CompareTo(value1);
U>        }
U>      }
U>      return 0;
U>    }


Можно посмотреть на пример, когда данная логика сравнения оказывается более приемлемой, чем логика, используемая в System.Collections.Comparer.Compare(object, object) (и System.Collections.Generic.Comparer<object>.Compare(object, object))?

ИМХО, проблем несколько — во первых, если ни один из аргументов не поддерживает сравнения, метод считает, что аргументы равны. Если же один из аргументов сравнение поддерживает, а другой — не поддерживает или имеет другой тип, то может возникнуть исключение. Логика, на мой взгяд, преочень сомнительная

Если же забиться на то, что по словам топикстартера и, значит, по условию задачи,

типы совпадают и для них определены операторы сравнения


неясно, зачем предлагать данную реализуцию, когда уже предложена такая
Comparer<object>.Default.Compare(x, y)

или можно воспользоваться такой:
Comparer.Default.Compare(x, y)

Help will always be given at Hogwarts to those who ask for it.
Re[3]: Сравнить два Object
От: Undying Россия  
Дата: 23.09.09 11:12
Оценка:
Здравствуйте, _FRED_, Вы писали:

_FR>неясно, зачем предлагать данную реализуцию, когда уже предложена такая

_FR>
Comparer<object>.Default.Compare(x, y)


Согласен, стандартная реализация лучше.

А для сравнения двух массивов object'ов что-нибудь стандартное есть?
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.