# lists and sequences

In this section we give an overview of the use of lists of all types, including:

## lists

A list is a handy way to store a series of things. We create one by separating the elements of the series by commas and surrounding the series with braces.
 ```i1 : x = {a,b,c,d,e} o1 = {a, b, c, d, e} o1 : List```
We retrieve the length of a list with the operator # or with the function length.
 ```i2 : #x o2 = 5``` ```i3 : length x o3 = 5```
We use the expression x#n to obtain the n-th element of x. The elements are numbered consecutively starting with 0. Alternatively, they are numbered consecutively ending with -1.
 ```i4 : x#2 o4 = c o4 : Symbol``` ```i5 : x#-2 o5 = d o5 : Symbol```
The functions first and last retrieve the first and last elements of a list.
 ```i6 : first x o6 = a o6 : Symbol``` ```i7 : last x o7 = e o7 : Symbol```

Omitting an element of a list causes the symbol null to be inserted in its place.

 ```i8 : g = {3,4,,5} o8 = {3, 4, , 5} o8 : List``` ```i9 : peek g o9 = {3, 4, null, 5}```

Lists can be used as vectors, provided their elements are the sorts of things that can be added and mutliplied.

 ```i10 : 10000*{3,4,5} + {1,2,3} o10 = {30001, 40002, 50003} o10 : List```
If the elements of a list are themselves lists, we say that we have a nested list.
 ```i11 : y = {{a,b,c},{d,{e,f}}} o11 = {{a, b, c}, {d, {e, f}}} o11 : List``` ```i12 : #y o12 = 2```
One level of nesting may be eliminated with flatten.
 ```i13 : flatten y o13 = {a, b, c, d, {e, f}} o13 : List```
A table is a list whose elements are lists all of the same length. The inner lists are regarded as rows when the table is displayed as a two-dimensional array with MatrixExpression.
 ```i14 : z = {{a,1},{b,2},{c,3}} o14 = {{a, 1}, {b, 2}, {c, 3}} o14 : List``` ```i15 : isTable z o15 = true``` ```i16 : MatrixExpression z o16 = | a 1 | | | | b 2 | | | | c 3 | o16 : Expression of class MatrixExpression```

## sequences

Sequence are like lists, except that parentheses are used instead of braces to create them and to print them. Sequences are implemented in a more efficient way than lists, since a sequence is created every time a function is called with more than one argument. Another difference is that new types of list can be created by the user, but not new types of sequence.
 ```i17 : x = (a,b,c,d,e) o17 = (a, b, c, d, e) o17 : Sequence``` ```i18 : #x o18 = 5``` ```i19 : x#2 o19 = c o19 : Symbol```
It is a bit harder to create a sequence of length 1, since no comma would be involved, and parentheses are also used for simple grouping of algebraic expressions.
 ```i20 : () o20 = () o20 : Sequence``` ```i21 : (a) o21 = a o21 : Symbol``` ```i22 : (a,b) o22 = (a, b) o22 : Sequence```
Most of the functions that apply to lists also work with sequences. We give just one example.
 ```i23 : append(x,f) o23 = (a, b, c, d, e, f) o23 : Sequence```
The functions toList and toSequence are provided for converting between lists to sequences.
 ```i24 : toList x o24 = {a, b, c, d, e} o24 : List``` ```i25 : toSequence oo o25 = (a, b, c, d, e) o25 : Sequence```
Other functions for dealing especially with sequences include sequence and deepSplice.

## arrays

An array is like a list, except that brackets are used instead of braces when entering or displaying an array, and arrays can't be used as vectors. Their main use is notational: for example, they appear in the construction of polynomial rings.
 ```i26 : v = [a,b,c] o26 = [a, b, c] o26 : Array``` ```i27 : v#2 o27 = c o27 : Symbol``` ```i28 : ZZ[a,b,c] o28 = ZZ[a, b, c] o28 : PolynomialRing```

## visible lists

Lists, sequences, and arrays are the three examples of what we call visible lists, which constitute the class VisibleList. Many functions are defined to act uniformly on visible lists.
 ```i29 : {a,b,c} o29 = {a, b, c} o29 : List``` ```i30 : class oo o30 = List o30 : Type``` ```i31 : parent oo o31 = VisibleList o31 : Type```

## basic lists

There is a type of list more general than a visible list, which we call a basic list. Basic lists can be used for representing new datatypes in a more secure way, since the many functions that act on lists and sequences do not act on basic lists.
 ```i32 : {a,b,c} o32 = {a, b, c} o32 : List``` ```i33 : class oo o33 = List o33 : Type``` ```i34 : parent oo o34 = VisibleList o34 : Type``` ```i35 : parent oo o35 = BasicList o35 : Type```
We can make a basic list with the new operator.
 ```i36 : new BasicList from {a,b,c} o36 = BasicList{a, b, c} o36 : BasicList```
Similarly, we can make a new type of basic list, called Container, say.
 ```i37 : Container = new Type of BasicList o37 = Container o37 : Type```
We can make a new list of type Container.
 ```i38 : t = new Container from {a,b} o38 = Container{a, b} o38 : Container```
Some functions work on basic lists.
 ```i39 : join(t,t) o39 = Container{a, b, a, b} o39 : Container```
We can make a new method for the operator ++, say, that will join two such lists.
 `i40 : Container ++ Container := join;` ```i41 : t ++ t o41 = Container{a, b, a, b} o41 : Container```

## mutable lists

The elements of a basic list cannot normally be replaced by others. However, there is a certain type of basic list, called a mutable list (of class MutableList), whose elements can be changed. Because the elements of a mutable list can be changed, circular structures can be created that would cause a print routine to go into an infinite loop. We avoid such infinite loops by not printing out the contents of mutable lists. Instead, one uses peek to display the elements in a controlled way.
 ```i42 : s = new MutableList from {a,b,c} o42 = MutableList{...3...} o42 : MutableList``` ```i43 : peek s o43 = MutableList{a, b, c}``` `i44 : s#2 = 1234;` ```i45 : s o45 = MutableList{...3...} o45 : MutableList``` ```i46 : peek s o46 = MutableList{a, b, 1234}```
Because the contents of mutable lists are not printed, they can be used as containers for big things that one normally doesn't want printed. For this purpose we have a special type of mutable list called a bag (of class Bag), that displays, when printed, a little information about its contents.
 ```i47 : Bag {100!} o47 = {*a bagged integer*} o47 : Bag``` ```i48 : peek oo o48 = Bag{9332621544394415268169923885626670049071596826438162146859296389521 ----------------------------------------------------------------------- 75999932299156089414639761565182862536979208272237582511852109168640000 ----------------------------------------------------------------------- 00000000000000000000}```

## summary

We can see the hierarchy of types mentioned above using showStructure.
 ```i49 : showStructure(List,Sequence,Array,Container,MutableList,Bag,BasicList) o49 = Thing : BasicList : Container MutableList : Bag VisibleList : Array List Sequence o49 : Descent```

#### manipulating lists and sequences

• append -- append an element to a list
• between -- insert something between elements of a list
• delete -- delete elements of a list
• drop -- drop some elements from a list or sequence
• flatten -- flatten a list by unnesting lists
• fold -- apply binary operator repeatedly
• join -- join lists
• List | List -- join lists, sequences or arrays
• mingle -- mingle elements of several lists
• pack -- pack elements of a list into shorter ones
• prepend -- add an element to the beginning of a list
• reverse, see reverse(BasicList) -- reverse a list
• rsort -- sort a list or matrix in reverse order
• sort -- sort a list or columns of a matrix
• subtable -- extract a subtable from a table
• table -- make a table (nested list)
• take -- take some elements from a list
• unique -- eliminate duplicates from a list