Assignment 1

Simple Assignment 2

Design Issues for Assignment 2

Assignment Operator. 3

Languages. 3

Multiple Assignment 3

Conditional Targets. 4

Conditional Value Assignment 4

Simultaneous Assignment 5

Parallel Assignment 6

Assignment as an Expression. 8

Multiple Assignment Problems. 9

Questions: 10

Answers. 11

Multiple Targets. 11

COBOL Relative MOVE.. 14

COBOL De-Editing. 14

Assignment Conversion. 14

Unary Assignment Operators. 17

Compound Assignment Operators. 18

Java Compound Assignment Operators. 19

Other Compound Assignment Operators. 20

Questions. 20

What Can Be Assigned?. 20

Operand Evaluation. 21

Character String Assignment 21

Functions on Left Side. 21

Designation Assignment Types. 21

Compound Assignment 22

Assignment by Sharing. 22

Questions. 22

 

Creative Commons License
This work is licensed under a
Creative Commons Attribution-No Derivative Works 3.0 United States License.

Copyright: Dennie Van Tassel 2008.

Please send suggestions and comments to dvantassel@gavilan.edu

 

Assignment

 

Assignment (hours = 40) may seem like one of the simplest of operations, but assignment has such universal use, and thus results in wide solutions to some of the problems involved. Examples of choices are simple assignment (assign one value to one variable) or multiple assignments (assign one value to several variables). There are also conditional assignments of values and variables in some languages. When we have a language that has different forms of assignment (compound, multiple) there are serious issues about exactly when the operands are evaluated. Finally, there is the question about exactly what can be assigned, such as only simple variables, or maybe arrays, structures, or objects.

 

The assignment statement is the most common type of statement found in programs. In an early study of statement types, Knuth found that 51% of the statements used in FORTRAN programs are assignment statements. The next two percentages were 8.5% for IF statements and 8% for GOTO statements.[1] While these statistics are probably different in modern languages, assignment is still the most commonly used statement.

 

Simple Assignment

At its simplest form, assignment looks something like:

 

     variable = expression

     count = 0

 

The expression or the right-hand value (called the r-value) is evaluated, and that value is placed in the item on the left-hand side (often called the l-value). The right expression needs to be a constant, variable, or expression that can produce a value. The l-value must be something that has memory to store a value. The expression on the right is also called the source of the assignment, and the left-hand side is called the destination of the assignment. L-value is also referred to as the location value, since that is the location where something is stored. And r-value is also called the read-value since that value needs to be read. But this last set of terminology seems rare.

 

Design Issues for Assignment

Here are a few design issues for assignment:

 

  • What symbol(s) will we use for assignment? This is especially of interest in contrast to equal comparison. There have been a lot of different choices here.
  • What can be assigned? Possible examples are constants, expressions, structures, arrays, and objects.
  • What can assignment accept? The question looks similar to the previous question but is different, since often only simple variables can be on the left side.
  • What types of assignments are allowed? Examples are simple assignment, multiple assignment, simultaneous assignment, and assignment by sharing.
  • What types of coercions are allowed? Assignment often requires coercion, such as when we assign an integer to a floating-point variable and vice versa.
  • When are operands evaluated? This becomes a very complicated question for the various forms of multiple assignment.

 

Now we will look at these interesting questions about assignment. The first question is what do we use for the assignment operator? The related question is how do we differentiate assignment (count=1) from comparison? If you immediately jumped on the C bandwagon of using = for assignment and == for comparison, then I can ask if you have ever been burnt by something like this?

 

   while (count=1) . . . // one equal symbol.

 

which will probably get us a nice infinite loop since we meant to use

 

   while (count==1) . . . // two equal symbols.

 

This code is a good example of how a language design issue can have major impact on programming productivity and program readability. [=== what is term for making sure things are different enough so not mistaken???]

 

Assignment Operator

Since we (and the compiler) need to be able to distinguish assignment (B = 5) and comparison IF (B==5)…,, then we need to look carefully at what we choose for these two operators. The Pascal family (Ada, Modula, etc.,) use := (colon and equal) for assignment which seems like a nice solution. Thus we use

 

     COST := 5

 

for assignment. This use clearly indicates it is assignment and not equality, and avoids the problem of mixing up an assignment test in comparison operations with an equality test.

Table x.1 lists some of the operators used for assignment in various languages.

 

Assignment Operator

Languages

a = b

Java, C++, Perl, FORTRAN, BASIC

a := b

Pascal, Ada, ALGOL

a <- b

APL, Smalltalk

(setq a b)

Lisp  

MOVE B TO A

COBOL

set a b

Tcl

Assignment Operators

Table x.1

 

While the Pascal family use of := seems like the best choice to me, the simple = symbol has won in most modern languages.

 

Multiple Assignment

Multiple assignment is one of the simplest assignment variations, but is not available in all languages. Early ALGOL contributed the concept.

 

     x := y := z := 0;

 

ALGOL also used := to show assignment instead of =, which they use for equality tests. For present day languages, we indicate multiple assignments in its simple form as follows:

 

     A = B = C = D = 0

 

We can make it slightly more complicated by including the same variable (B) in the variable list on the left and the expression:

 

     A = B = C = B + 5

 

In this case B+5 is evaluated and all the variables are set to that value. This reminds us that assignment is evaluated from the right to the left.

 

In Python this is called chained assignment. We are assigning several variables to the same value. For example, if we have something similar to this:

 

   x = y = fun();

 

it may not be the same as:

 

   y = fun();

   x = fun();

 

since the function fun()can return different values.

 

Conditional Targets

A conditional target is when a condition is used to decide which variable to use as the l-value or target. Java and C++ allow conditional targets by use of the conditional (ternary) operation. Thus we can do something similar to:

 

   (n < 0) ? maxx : maxy = 0;

 

So either the variable maxx or maxy is set to zero depending on the condition. This can be done as follows with an if statement:

 

   if (n < 0) maxx = 0; else maxy = 0;

 

but the first way is a lot neater and allowed me to bring up conditional targets.

 

Conditional Value Assignment

The opposite of conditional target may be conditional value assignment, where a condition is used to determine which r-value is assigned to the single l-value. The ternary operation is also used for this as follows:

 

   rates = (age < 21) ? 1.25 : 1.00;

 

In this statement the value 1.25 is assigned to the variable rates when age is less than 21. The general form of this type of statement is:

 

   result = (condition) ? a: b;

 

So either value of variable a or value of variable b is assigned to variable result depending on the condition. This can be done as follows with an if statement:

 

   if (condition)  v = a; else v = b;

   if (age < 21) rates = 1.25; else rates = 1.00;

 

This is not actually a new type of an assignment statement, but a variation on normal assignment.

 

Simultaneous Assignment

Perl, Ruby, and Python use a version of multiple assignment called simultaneous assignment, so different values are assigned “simultaneously.” In Perl, variable names start with a dollar sign, so instead of the variable tax, in Perl it would be $tax. So here is what Perl does:

 

            ($tax, $count, $size) = (0.085, 0, 100);

 

This sets $tax to 0.085, $count to zero, and $size to 100. Character strings can be assigned in the same ways:

 

   ($first, $middle, $last) = (“Edgar”, “Allan”, “Poe”); 

 

This is called list assignment in Perl. In Perl, additional variables on the left side are assigned undef. For example:

 

   ($x, $y, $z) = (1, 2);

 

This will assign 1 to $x and assign 2 to $y, and then assign undef to $z since there are two values on the right side, and there are three variables on the left side.

 

Simultaneous assignment has several interesting uses. Besides statements like the above, we can do this in Python:

 

   (x, y) = (y, x)

 

which will interchange the two variables, and it works the way we would want it to, switching the two values.

 

In Ruby parentheses are not necessary, so we do the following:

 

   foo, bar, boo = 1, 2, 3

 

Which assigns 1 to foo, 2 to bar, and 3 to boo.

 

This type of assignment can also introduce some interesting problems. What happens in the following code?

 

   ($x, $x) = (5, 6);

 

In this example, we assign 5 to $x, and also assign 6 to variable $x. In this case, the variable $x will end up with the value 6 in it. Thus in all these assignment statements that are similar to this simultaneous assignment, we have the following:

 

   (v1, v2) = (e1, e2)

 

There are at least two ways to process the above statement. The first way is evaluate expression-1 and then evaluate expression-2, and then do the assignments. The other way is to evaluate expression-1 on the right side, assign it to variable-1, then evaluate expression-2, and assign that value to variable-2 on the left side. If the expressions have side affects or change each other, we get different results depending on what method of evaluation is used.

 

Perl arrays use an @ symbol to precede the array name and use square brackets for the subscript or array index. Thus @a[$k] represents an array and $k is a valid index of a Perl array. Then what happens in the following two examples (assuming $k=0 to start with):

 

   (@a[$k], $k) = (35, 2)

   ($k, @a[$k]) = (2, 35)

 

and is the result the same in both statements? Work through these by hand to see what result you get. Then you may want to find a Perl manual and Perl interpreter to find out how it works. There are some problems here about determining exactly when values are processed and assigned. For example, are the operands on the left side evaluated first or are the operands on the right side evaluated first?

 

Another interesting example is

   (@a[$k], @a[$j]) = (5, 8)

What happens when the subscripts $k and $j are equal? I think the order of evaluation becomes very important here. Simultaneous assignment is a rather rare version of assignment, but available in a few languages.

 

Parallel Assignment

The language Ruby does something similar to simultaneous assignment, but they call it parallel assignment. Their form looks as follows:

 

   a, b, c = 1, 2, 3

 

So the variable a will be assigned the value 1, then the variable b will be assigned the value 2, etc. They carefully define exactly what happens. If there are extra values on the right, those extra values are ignored. If there are extra variables on the left, the extra variables are set to nil. We can do useful things like interchange two variables, as follows:

 

   a, b = b, a

 

and what we hope will happen, will happen. Notice that the assignments must be done in parallel. Otherwise, both the variables would have the same value when done.

 

Ruby also carefully defines the order of the operations. The rules are the values on the right are evaluated in the order that they appear before any assignment is done to the variables on the left. Here is an example, where knowing exactly what happens is necessary:

 

   w, x, y, = z, (z += 1), z += 1)

 

Assuming z starts with the value 5, what values will be assigned? If you are interested in parallel assignment it will be useful to look at exactly how Ruby does it. There is a bit more too it, especially when arrays are involved. Ruby also has nested assignment where the left-hand side of an assignment may contain a parenthesized list of terms.[2]

 

Pascal has a similar command. We can do the same sort of command as follows:

 

   var1, var2 := 12, 15;

 

which will assign 12 to the var1 and 15 to var2. We can also do the useful

 

   var1, var2 := var2, var1;

 

which will swap the two values without the need of a temporary variable. Trace through what has to happen here for this to work.

 

Ada has done things a little differently. Assume we want to declare two integer variables and set both variables to 10. We can do this in C++ and Ada as follows:

 

C++:  int i = 10, j = 10;

Ada: I, J: INTEGER := 10;

 

In C++ we can assign different values to variables in the same declaration, but in Ada we would need to use two different declarations:

 

C++:  int x = 25, z = 76;

Ada:  X: INTEGER := 25;

     Z: INTEGER := 76;

 

When we declare two or more variables in one statement, both values get the same value. For example:

 

Ada:  X, W: INTEGER := P;

 

Since both variables on the left need a value, is the value on the right calculated once or twice? Either way seems reasonable:

 

  1. Since the expression is written once, it needs to be calculated only once.
  2. Or since we need the value twice, it should be calculated twice.

 

The problem only appears when the expression on the right has side effects such as a function call or increment. Here is some pseudocode (not real Ada code) that illustrates the problem:

 

  X, W: INTEGER := b++; -- Does X and W get the same value?

  M, N: INTEGER := PRT(P) -- PRT IS A FUNCTION THAT PRINTS.

 

What Ada actually does is covered in the exercises. What do you think should happen?

 

 

Assignment as an Expression

Multiple assignment can be implemented in different ways. One way is just assigning all the variables the value on the far right:

 

   a = b = c = 0;

 

Another way to implement multiple assignment is the way it is done in the C family, where assignment returns a value which is the same as the value assigned the target. This can be illustrated by printing an assignment statement as follows:

 

   cout << “value = “ << k = 5 << endl;

 

The variable k will be assigned the value 5, and the result printed will be:

 

   value = 5

 

Since assignment expressions return a value, we can use that to create:

 

   a = b = c = 0;

 

and since assignment is associative from right to left we obtain:

 

   a = (b = (c = 0));

 

So the variable c is assigned the value zero, then zero is returned and zero is assigned the variable b, and so forth.

 

While the above use of value from the assignment expression seems useful and correct, this characteristic can be used in stranger and more questionable ways:

 

   price = cost + (profit = 10) + cost * 0.12;

 

In this somewhat bizarre use, the variable profit will be assigned 10, and then 10 will be added in the statement.

 

Multiple Assignment Problems

If you casually read a PL/I (or BASIC) program (which you probably do often), you might see something like this:

 

     A = B = C;

 

and erroneously assume it is multiple assignment. But both BASIC and PL/I use the equal sign for both assignment and comparison. So the first “equal” sign (A = ... ) is assignment, and the second “equal” sign is comparison, so PL/I will compare the variable B and C, and assign variable A either true or false!

 

Early BASIC uses the = symbol for both assignment and comparison. For example:

 

     a = 18

     if (a = 18) then ....

 

Later Boolean type was added and also longer variable names. Now we have the following possible Visual Basic statements:

 

     dim youth as boolean

     youth = age < 18

 

which does not seem too unusual. Since age < 18 is a comparison, we would expect a true or