IBM Streams 4.3.0

Tuples

A tuple is a sequence of attributes, and an attribute is a named value.

For example, the tuple { sym="Fe", no=26 } consists of two attributes sym="Fe" and no=26. The type for this tuple is tuple<rstring sym, int32 no>. Tuples are similar to database rows in that they have a sequence of named and typed attributes. Tuples differ from objects in Java™ or C++ in that they do not have methods. You can access the attributes of a tuple with dot notation. For example, given a tuple t of type tuple<rstring sym, int32 no>, the expression t.sym yields the sym attribute.

Attributes within a tuple are ordered: tuple<int32 x, int32 y> and tuple<int32 y, int32 x> are two different types. But this ordering is hidden at the language level, and can be changed by the runtime implementation for optimization. The only way a program can depend on the declaration order of attributes is in source operators that read from a text file formatted as comma-separated values (csv).

Tuple types can extend other tuple types, by adding more attributes. For example:

type Loc2d = tuple<int32 x, int32 y>;
type Loc3d = Loc2d, tuple<int32 z>;

The resulting type Loc3d is equivalent to tuple<int32 x, int32 y, int32 z>. In tuple extension, if the tuples have an attribute with the same name and type, the resulting tuple contains that attribute once, in the position of its leftmost occurrence. It is an error for the tuples in tuple extension to have attributes with the same name but different types.

In tuple extension, the identifier can also be the name of a stream as a shorthand for the type of the tuples in that stream. For example:

composite Main {
  type  LocWithId = LocStream, tuple<rstring id>;
  graph stream<int32 x, int32 y> LocStream = Beacon() {}
} 

The resulting type LocWithId is equivalent to tuple<int32 x, int32 y, rstring id>. The syntax for tuple types is:

tupleType     ::= ‘tuple' ‘<' tupleBody ‘>'
tupleBody     ::= attributeDecl+,             # attributes
                | ( ID | tupleType )+,        # tuple type extension
attributeDecl ::= type ID

In other words, the body of the tuple type either consists of a comma-separated list of attribute declarations, or a comma-separated list of tuple types, either by name or written in-place. This extension syntax deviates from the inheritance syntax in object-oriented languages like Java because it needs to be light weight and nestable. Tuple types can be arbitrarily nested. In other words, their attributes can be of any type, including other composite types, even other tuple types. For example:

type Loc2d  = tuple<int32 x, int32 y>;
type Sensor = tuple<rstring color, tuple<Loc2d, tuple<int32 z>> loc>;

After the type is extended, Loc2d with a z attribute, and using the whole thing as a loc attribute, the resulting type Sensor is tuple<rstring color, tuple<int32 x, int32 y, int32 z> loc>. For example, given a variable Sensor s, the expression s.loc.z accesses the z-coordinate.

The explicit tuple<...> type constructor can be omitted at the top level of a type definition. For more information, see Type definitions. That means that the previous example can also be written like:

type Loc2d  = int32 x , int32 y ;
type Sensor = rstring color, tuple<Loc2d, tuple<int32 z>> loc;

The literal syntax for tuple values is as follows:

tupleLiteral ::= ‘{' ( ID ‘=' expr)*, ‘}' # e.g. { x=1, y=2 }

The empty tuple literal, {}, is only valid in casts or initialization. For example, mutable Loc3d myLocation = {}; zero-initializes myLocation, equivalent to mutable Loc3d myLocation = {x=0, y=0, z=0};.