You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@mina.apache.org by Stuart Scott <st...@vuetec.com> on 2008/02/19 11:33:02 UTC

IoBuffer getEnum/putEnum using signed values

I noticed that the various getEnum/putEnum methods in IoBuffer use the
signed values of the various data types. As Enums cannot have negative
ordinals would it not be more useful to use the unsigned version of the
data type?

This would be useless for getEnumInt/putEnumInt as an Enum can't be that
large but it might be useful for getEnumShort/putEnumShort and
getEnum/putEnum.

For example:

@Override
public <E extends Enum<E>> E getEnum(Class<E> enumClass) {
    return toEnum(enumClass, getUnsigned());
}

@Override
public <E extends Enum<E>> E getEnum(int index, Class<E> enumClass) {
    return toEnum(enumClass, getUnsigned(index));
}

@Override
public <E extends Enum<E>> E getEnumShort(Class<E> enumClass) {
    return toEnum(enumClass, getUnsignedShort());
}

@Override
public <E extends Enum<E>> E getEnumShort(int index, Class<E> enumClass) {
    return toEnum(enumClass, getUnsignedShort(index));
}

@Override
public IoBuffer putEnum(Enum<?> e) {
    if (e.ordinal() > 0xff) {
        throw new IllegalArgumentException(enumConversionErrorMessage(e,
                "byte"));
    }
    return put((byte) e.ordinal());
}

@Override
public IoBuffer putEnum(int index, Enum<?> e) {
    if (e.ordinal() > 0xff) {
        throw new IllegalArgumentException(enumConversionErrorMessage(e,
                "byte"));
    }
    return put(index, (byte) e.ordinal());
}

@Override
public IoBuffer putEnumShort(Enum<?> e) {
    if (e.ordinal() > 0xffff) {
        throw new IllegalArgumentException(enumConversionErrorMessage(e,
                "short"));
    }
    return putShort((short) e.ordinal());
}

@Override
public IoBuffer putEnumShort(int index, Enum<?> e) {
    if (e.ordinal() > 0xffff) {
        throw new IllegalArgumentException(enumConversionErrorMessage(e,
                "short"));
    }
    return putShort(index, (short) e.ordinal());
}

Stuart

Re: IoBuffer getEnum/putEnum using signed values

Posted by Emmanuel Lecharny <el...@gmail.com>.
James Apfel wrote:
> BTW. storing & retrieving of Enums through ordinals will fail if one
> changes the order of the fields (or prepends new fields).
>   
this is the reason why you just affect those kind of numbers explicitly 
if you want to be protected against such problems, like in :

public enum Numbers {
    ONE(1),
    TWO(2);

    private int ordinal;

    private Numbers( int ordinal ) {
        this.ordinal = ordinal;
    }
 
    public int getOrdinal() {
        return ordnial;
    }
}


-- 
--
cordialement, regards,
Emmanuel Lécharny
www.iktek.com
directory.apache.org



Re: IoBuffer getEnum/putEnum using signed values

Posted by James Apfel <ja...@gmail.com>.
BTW. storing & retrieving of Enums through ordinals will fail if one
changes the order of the fields (or prepends new fields).

enum Numbers {
    ONE, // ordinal=0
    TWO, // ordinal=1
}

IoBuffer buffer;
buffer.putEnum(Numbers.ONE);
buffer.flip();

Now I'm changing something in my Numbers Enum

enum Number {
    ZERO, // ordinal=0
    ONE, // ordinal=1
    TWO, // ordinal=2
}

Number num = buffer.getEnum(Number.class);
System.out.println(num); // Expected ONE but is ZERO

James

On Wed, Feb 20, 2008 at 6:20 PM, Emmanuel Lecharny <el...@gmail.com> wrote:
>
> Tuure Laurinolli wrote:
>  > Stuart Scott wrote:
>  >> I noticed that the various getEnum/putEnum methods in IoBuffer use the
>  >> signed values of the various data types. As Enums cannot have negative
>  >> ordinals would it not be more useful to use the unsigned version of the
>  >> data type?
>  >
>  > What unsigned version would that be? There is only one unsigned
>  > integral data type in Java, and that is char (JLS 4.2.1). Also,
>  > handling shorter integral types in Java is tiresome, since they get
>  > cast to int as soon as you apply some operator to them (JLS 15.x).
>  Also you can store negative value in an enum, assuming you affect this
>  value instead of using the default incremental value.
>  >
>  >
>
>
>  --
>  --
>  cordialement, regards,
>  Emmanuel Lécharny
>  www.iktek.com
>  directory.apache.org
>
>
>

Re: IoBuffer getEnum/putEnum using signed values

Posted by Emmanuel Lecharny <el...@gmail.com>.
Tuure Laurinolli wrote:
> Stuart Scott wrote:
>> I noticed that the various getEnum/putEnum methods in IoBuffer use the
>> signed values of the various data types. As Enums cannot have negative
>> ordinals would it not be more useful to use the unsigned version of the
>> data type?
>
> What unsigned version would that be? There is only one unsigned 
> integral data type in Java, and that is char (JLS 4.2.1). Also, 
> handling shorter integral types in Java is tiresome, since they get 
> cast to int as soon as you apply some operator to them (JLS 15.x).
Also you can store negative value in an enum, assuming you affect this 
value instead of using the default incremental value.
>
>


-- 
--
cordialement, regards,
Emmanuel Lécharny
www.iktek.com
directory.apache.org



Re: IoBuffer getEnum/putEnum using signed values

Posted by Tuure Laurinolli <tu...@indagon.com>.
Stuart Scott wrote:
> I noticed that the various getEnum/putEnum methods in IoBuffer use the
> signed values of the various data types. As Enums cannot have negative
> ordinals would it not be more useful to use the unsigned version of the
> data type?

What unsigned version would that be? There is only one unsigned integral 
data type in Java, and that is char (JLS 4.2.1). Also, handling shorter 
integral types in Java is tiresome, since they get cast to int as soon 
as you apply some operator to them (JLS 15.x).


Re: IoBuffer getEnum/putEnum using signed values

Posted by Mike Heath <mh...@apache.org>.
Niklas Therning wrote:
> Mike Heath wrote:
>> I made this fix per your request.  You can now use getEnum/putEnum enums
>> with an ordinal value > 127 for bytes and enums with an ordinal value >
>> 65535 for shorts.
>>   
> Wow, it's fascinating how you managed to use shorts for values larger
> than 65535! Please explain ;-)


s/65535/32767/

In the future please read my mind and not what I type. ;)

-Mike

Re: IoBuffer getEnum/putEnum using signed values

Posted by Niklas Therning <ni...@trillian.se>.
Mike Heath wrote:
> I made this fix per your request.  You can now use getEnum/putEnum enums
> with an ordinal value > 127 for bytes and enums with an ordinal value >
> 65535 for shorts.
>   
Wow, it's fascinating how you managed to use shorts for values larger 
than 65535! Please explain ;-)

/Niklas


Re: IoBuffer getEnum/putEnum using signed values

Posted by Mike Heath <mh...@apache.org>.
I made this fix per your request.  You can now use getEnum/putEnum enums
with an ordinal value > 127 for bytes and enums with an ordinal value >
65535 for shorts.

Thanks for the fix.

-Mike

Stuart Scott wrote:
> I noticed that the various getEnum/putEnum methods in IoBuffer use the
> signed values of the various data types. As Enums cannot have negative
> ordinals would it not be more useful to use the unsigned version of the
> data type?
> 
> This would be useless for getEnumInt/putEnumInt as an Enum can't be that
> large but it might be useful for getEnumShort/putEnumShort and
> getEnum/putEnum.
> 
> For example:
> 
> @Override
> public <E extends Enum<E>> E getEnum(Class<E> enumClass) {
>     return toEnum(enumClass, getUnsigned());
> }
> 
> @Override
> public <E extends Enum<E>> E getEnum(int index, Class<E> enumClass) {
>     return toEnum(enumClass, getUnsigned(index));
> }
> 
> @Override
> public <E extends Enum<E>> E getEnumShort(Class<E> enumClass) {
>     return toEnum(enumClass, getUnsignedShort());
> }
> 
> @Override
> public <E extends Enum<E>> E getEnumShort(int index, Class<E> enumClass) {
>     return toEnum(enumClass, getUnsignedShort(index));
> }
> 
> @Override
> public IoBuffer putEnum(Enum<?> e) {
>     if (e.ordinal() > 0xff) {
>         throw new IllegalArgumentException(enumConversionErrorMessage(e,
>                 "byte"));
>     }
>     return put((byte) e.ordinal());
> }
> 
> @Override
> public IoBuffer putEnum(int index, Enum<?> e) {
>     if (e.ordinal() > 0xff) {
>         throw new IllegalArgumentException(enumConversionErrorMessage(e,
>                 "byte"));
>     }
>     return put(index, (byte) e.ordinal());
> }
> 
> @Override
> public IoBuffer putEnumShort(Enum<?> e) {
>     if (e.ordinal() > 0xffff) {
>         throw new IllegalArgumentException(enumConversionErrorMessage(e,
>                 "short"));
>     }
>     return putShort((short) e.ordinal());
> }
> 
> @Override
> public IoBuffer putEnumShort(int index, Enum<?> e) {
>     if (e.ordinal() > 0xffff) {
>         throw new IllegalArgumentException(enumConversionErrorMessage(e,
>                 "short"));
>     }
>     return putShort(index, (short) e.ordinal());
> }
> 
> Stuart
>