盒装原始值的动态比较
Dynamic comparison of boxed primitive values
我需要对两个原始(数字!)类型(都装箱为对象)进行泛型比较以找到更大的一个。
我不能使用泛型,因为我只获取对象,但我知道未装箱的值是原始数字(int、short、long、float 等),所以我可以转换为 IComparable。
我怎样才能比较那些? CompareTo() 会抛出错误,因为它们是不同的类型,但 ChangeType 会导致 OverflowException...?
public static int Compare(object value1, object value2)
{
//e.g. value1 = (object)(int)1; value2 = (object)(float)2.0f
if (value1 is IComparable && value2 is IComparable)
{
return (value1 as IComparable).CompareTo(value2);
//throws exception bc value1.GetType() != value2.GetType()
}
throw new ArgumentException();
}
也许是
public static int Compare(object value1, object value2)
{
if (value1 is double || value2 is double)
{
double d1 = Convert.ToDouble(value1);
double d2 = Convert.ToDouble(value2);
return d1.CompareTo(d2);
}
if (value1 is float || value2 is float)
{
float f1 = Convert.ToSingle(value1);
float f2 = Convert.ToSingle(value2);
return f1.CompareTo(f2);
}
long x1 = Convert.ToInt64(value1);
long x2 = Convert.ToInt64(value2);
return x1.CompareTo(x2);
}
byte、short、int类型都可以转为long而不损失精度。
这是另一种方式:
public void test() {
Object o1 = 5465.0;
Object o2 = 5465;
Object o3 = 5465l;
Object o4 = "5465";
System.out.println(compare(o1, o2));
System.out.println(compare(o1, o3));
System.out.println(compare(o2, o3));
System.out.println(compare(o3, o4));
}
public Double convertNumber(Object o) {
if (o instanceof Double) {
return (Double) o;
} else if (o instanceof Long) {
return ((Long) o).doubleValue();
} else if (o instanceof Integer) {
return ((Integer) o).doubleValue();
} else if (o instanceof String) {
try {
return Double.parseDouble((String) o);
} catch (Exception e) {
}
}
return null;
}
public int compare(Object o1, Object o2) {
if (o1 == null && o2 == null)
return 0;
if (o1 == null || o2 == null)
return -1;
Double asNumber1 = convertNumber(o1);
if (asNumber1 == null)
return String.valueOf(o1).compareTo(String.valueOf(o2));
Double asNumber2 = convertNumber(o2);
return asNumber2 == null ? -1 : asNumber1.compareTo(asNumber2);
}
我需要对两个原始(数字!)类型(都装箱为对象)进行泛型比较以找到更大的一个。 我不能使用泛型,因为我只获取对象,但我知道未装箱的值是原始数字(int、short、long、float 等),所以我可以转换为 IComparable。
我怎样才能比较那些? CompareTo() 会抛出错误,因为它们是不同的类型,但 ChangeType 会导致 OverflowException...?
public static int Compare(object value1, object value2)
{
//e.g. value1 = (object)(int)1; value2 = (object)(float)2.0f
if (value1 is IComparable && value2 is IComparable)
{
return (value1 as IComparable).CompareTo(value2);
//throws exception bc value1.GetType() != value2.GetType()
}
throw new ArgumentException();
}
也许是
public static int Compare(object value1, object value2)
{
if (value1 is double || value2 is double)
{
double d1 = Convert.ToDouble(value1);
double d2 = Convert.ToDouble(value2);
return d1.CompareTo(d2);
}
if (value1 is float || value2 is float)
{
float f1 = Convert.ToSingle(value1);
float f2 = Convert.ToSingle(value2);
return f1.CompareTo(f2);
}
long x1 = Convert.ToInt64(value1);
long x2 = Convert.ToInt64(value2);
return x1.CompareTo(x2);
}
byte、short、int类型都可以转为long而不损失精度。
这是另一种方式:
public void test() {
Object o1 = 5465.0;
Object o2 = 5465;
Object o3 = 5465l;
Object o4 = "5465";
System.out.println(compare(o1, o2));
System.out.println(compare(o1, o3));
System.out.println(compare(o2, o3));
System.out.println(compare(o3, o4));
}
public Double convertNumber(Object o) {
if (o instanceof Double) {
return (Double) o;
} else if (o instanceof Long) {
return ((Long) o).doubleValue();
} else if (o instanceof Integer) {
return ((Integer) o).doubleValue();
} else if (o instanceof String) {
try {
return Double.parseDouble((String) o);
} catch (Exception e) {
}
}
return null;
}
public int compare(Object o1, Object o2) {
if (o1 == null && o2 == null)
return 0;
if (o1 == null || o2 == null)
return -1;
Double asNumber1 = convertNumber(o1);
if (asNumber1 == null)
return String.valueOf(o1).compareTo(String.valueOf(o2));
Double asNumber2 = convertNumber(o2);
return asNumber2 == null ? -1 : asNumber1.compareTo(asNumber2);
}