[Info-vax] C limitations, was: Re: VMS process communication

Arne Vajhøj arne at vajhoej.dk
Wed Mar 29 19:22:03 EDT 2023


On 3/29/2023 11:37 AM, Johnny Billquist wrote:
> On 2023-03-28 00:46, Arne Vajhøj wrote:
>> On 3/27/2023 6:16 PM, Johnny Billquist wrote:
>>> On 2023-03-27 14:27, Simon Clubley wrote:
>>>> enums are integers, not a type.
>>>
>>> Not sure I consider the enum thing to be much of a deal. Unless we 
>>> compare to Ada, which is the only language I've seen which really do 
>>> enums properly as its own type.
>>
>> Java enums are also very much non-int.
> 
> I can't remember Java enough to be sure, but I don't think they went as 
> far as Ada. What happens in Java if you print out the value of an enum 
> variable? Can you loop over it, and that is a loop that does not have an 
> integer loop counting? Can you read values into an enum, and do you then 
> type in the possible enums or else get an error? Can you use enums as 
> indexing in arrays? And nowhere does any numberness of the whole thing 
> shines through?
> 
> I thought Java was rather C-like...

Java use curly brackets, has the traditional if/switch/for/while/do
control structures and has char/short/int/long/float/double simple
data types.

But besides that it does not have that much in common with C.

Java enum's are not int's. But there are certain possibilities
to do stuff if one really wants to.

Let me explain.

First the very basic:

public enum Direction {
     North, South, West, East;
}

This is not a type with integer values 0,1,2,3 or 1,2,3,4.

The Java compiler generate something similar to
(not quite like this - I will come back to that):

public final class Direction extends Enum {
     public static final Direction North = new Direction();
     public static final Direction South = new Direction();
     public static final Direction West = new Direction();
     public static final Direction East = new Direction();
     private Direction() {
     }
}

So the values of the enum are really references/pointers to
dynamically allocated objects. Either 32 or 64 bit. And may
actually have different values in different applications due to
different memory usage when initialized.

They are very type safe though. It is not possible to assign
between different unrelated classes.

But some convenience features was added:
* a toString method that convert to String representation
* a values method that return an array of ordered values
   that can be iterated over
* a valueOf method that convert from String representation

$ type Nice.java
public class Nice {
     public static void main(String[] args) {
         Direction d0 = Direction.West;
         System.out.println(d0);
         for(Direction d1 : Direction.values()) {
             System.out.println("-" + d1);
         }
         Direction d2 = Direction.valueOf("West");
         System.out.println(d2);
     }
}
$ javac Nice.java
$ java "Nice"
West
-North
-South
-West
-East
West

That array of values can of course be abused to convert
to and from int.

$ type Hack.java
import java.util.Arrays;

public class Hack {
     public static void main(String[] args) {
         Direction[] alld = Direction.values();
         int ix = Arrays.asList(alld).indexOf(Direction.West);
         System.out.println(ix);
         System.out.println(alld[ix]);
     }
}
$ javac Hack.java
$ java "Hack"
2
West

But I don't think that is really bad. That is all
array functionality and has nothing to do with enum.

But worse is that to support the convenience methods then
the private constructor is not:

private Direction() {
}

but instead:

private Direction(String strval, int ordval)  {
     super(strval, ordval);
}

which opens up for some creative abuse of the internals
of Enum.

$ type DirtyHack.java
import java.lang.reflect.Field;

public class DirtyHack {
     public static void main(String[] args) throws NoSuchFieldException, 
SecurityException, IllegalArgumentException, IllegalAccessEx
ception {
         Direction d = Direction.West;
         Field f = d.getClass().getSuperclass().getDeclaredField("ordinal");
         f.setAccessible(true);
         int ix = (int)(Integer)f.get(d);
         System.out.println(ix);
         System.out.println(Direction.values()[ix]);
     }
}
$ javac DirtyHack.java
$ java "DirtyHack"
2
West

Nobody use those hacks in practice, because Java's
enum has support for having extra properties
because it is a class under the hood.

$ type XDirection.java
public enum XDirection {
     North(1001),
     South(1002),
     West(1003),
     East(1004);
     private int n;
     private XDirection(int n) {
         this.n = n;
     }
     public String toString() {
         return String.format("%s (%d)", super.toString(), n);
     }
     public int getN() {
         return n;
     }
}
$ javac "XDirection.java"
$ type Adv.java
public class Adv {
     public static void main(String[] args) {
         XDirection d0 = XDirection.West;
         System.out.println(d0 + " : " + d0.getN());
         for(XDirection d1 : XDirection.values()) {
             System.out.println("-" + d1 + " : " + d1.getN());
         }
         XDirection d2 = XDirection.valueOf("West");
         System.out.println(d2 + " : " + d2.getN());
     }
}
$ javac Adv.java
$ java "Adv"
West (1003) : 1003
-North (1001) : 1001
-South (1002) : 1002
-West (1003) : 1003
-East (1004) : 1004
West (1003) : 1003

I think that sort of explains Java enum.

One last thing - array indexes in Java are always int (signed
32 bit integer), so enums cannot be used as array index.

Arne











More information about the Info-vax mailing list