music |
| | OSdata.com |
assignment
summary
This subchapter looks at assignment.
Assignment statements and/or assignment operators are used to assign or modify the value of variables. Assignment statements often include arithmetic or computation expressions.
assignment
Assignment statements and/or assignment operators are used to assign or modify the value of variables. Assignment statements often include arithmetic or computation expressions.
basic assignment
The assignment statement transfers data from a source to a destination. The destination is usually a variable. In most languages the source can be a constant, variable, function, or expression.
The most basic version is assigning a constant number to a variable. In the following examples we will assign the value of zero (0) to a variable named x:
MOVE ZERO TO X.
-OR-
MOVE 0 TO X.
Note that unlike most programming languages, C does not have an assignment statement, but rather has an assignment operator. This allows assignment to be compacted into other programming constructs, which can lead to confusion.
One classic C mistake is using the assignment operator rather than the equality test in an if statement:
if (x == 0) dosomething(); /* tests to see if x is equal to zero
if (x = 0) dosomething(); /* assigns zero to x and tests to see if x is zero
This feature can be used to make very terse (and confusing) code:
while (*p++ = *q++) ;
The above loop copies copies data from one string or block of data to another until a zero is encountered. See while loops.
Brian Kernighan and Dennis Ritchie (the original creators of C) in their famous book The C Programming Language recommend writing only one statement per line, and using blanks around operators to clarify grouping.
Stanford C essentials
Stanford CS Education Library This [the following section until marked as end of Stanford University items] is document #101, Essential C, in the Stanford CS Education Library. This and other educational materials are available for free at http://cslibrary.stanford.edu/. This article is free to be used, reproduced, excerpted, retransmitted, or sold so long as this notice is clearly reproduced at its beginning. Copyright 1996-2003, Nick Parlante, nick.parlante@cs.stanford.edu.
Assignment Operator =
The assignment operator is the single equals sign (=).
i = 6;
i = i + 1;
The assignment operator copies the value from its right hand side to the variable on its left hand side. The assignment also acts as an expression which returns the newly assigned value. Some programmers will use that feature to write things like the following.
y = (x = 2 * x); // double x, and also put x's new value in y
Type Combination and Promotion
The integral types may be mixed together in arithmetic expressions since they are all basically just integers with variation in their width. For example, char and int can be combined in arithmetic expressions such as ('b' + 5). How does the compiler deal with the different widths present in such an expression? In such a case, the compiler promotes the smaller type (char) to be the same size as the larger type (int) before combining the values. Promotions are determined at compile time based purely on the types of the values in the expressions. Promotions do not lose information -- they always convert from a type to compatible, larger type to avoid losing information.
Pitfall -- int Overflow
I once had a piece of code which tried to compute the number of bytes in a buffer with the expression (k * 1024) where k was an int representing the number of kilobytes I wanted. Unfortunately this was on a machine where int happened to be 16 bits. Since k and 1024 were both int, there was no promotion. For values of k >= 32, the product was too big to fit in the 16 bit int resulting in an overflow. The compiler can do whatever it wants in overflow situations -- typically the high order bits just vanish. One way to fix the code was to rewrite it as (k * 1024L) -- the long constant forced the promotion of the int. This was not a fun bug to track down -- the expression sure looked reasonable in the source code. Only stepping past the key line in the debugger showed the overflow problem. Professional Programmers Language. This example also demonstrates the way that C only promotes based on the types in an expression. The compiler does not consider the values 32 or 1024 to realize that the operation will overflow (in general, the values dont exist until run time anyway). The compiler just looks at the compile time types, int and int in this case, and thinks everything is fine.
Truncation
The opposite of promotion, truncation moves a value from a type to a smaller type. In that case, the compiler just drops the extra bits. It may or may not generate a compile time warning of the loss of information. Assigning from an integer to a smaller integer (e.g.. long to int, or int to char) drops the most significant bits. Assigning from a floating point type to an integer drops the fractional part of the number.
char ch;
int i;
i = 321;
ch = i; // truncation of an int value to fit in a char
// ch is now 65
The assignment will drop the upper bits of the int 321. The lower 8 bits of the number 321 represents the number 65 (321 - 256). So the value of ch will be (char)65 which happens to be A.
The assignment of a floating point type to an integer type will drop the fractional part of the number. The following code will set i to the value 3. This happens when assigning a floating point number to an integer or passing a floating point number to a function which takes an integer.
double pi;
int i;
pi = 3.14159;
i = pi; // truncation of a double to fit in an int
// i is now 3
Pitfall -- int vs. float Arithmetic
Heres an example of the sort of code where int vs. float arithmetic can cause problems. Suppose the following code is supposed to scale a homework score in the range 0..20 to be in the range 0..100.
{
int score;
...// suppose score gets set in the range 0..20 somehow
score = (score / 20) * 100; // NO -- score/20 truncates to 0
...
Unfortunately, score will almost always be set to 0 for this code because the integer division in the expression (score/20) will be 0 for every value of score less than 20. The fix is to force the quotient to be computed as a floating point number
score = ((double)score / 20) * 100; // OK -- floating point division from cast
score = (score / 20.0) * 100; // OK -- floating point division from 20.0
score = (int)(score / 20.0) * 100; // NO -- the (int) truncates the floating
// quotient back to 0
Mathematical Operators
C includes the usual binary and unary arithmetic operators. See the appendix for the table of precedence. [Found in this book in the subchapter on order of precedence] Personally, I just use parenthesis liberally to avoid any bugs due to a misunderstanding of precedence. The operators are sensitive to the type of the operands. So division (/) with two integer arguments will do integer division. If either argument is a float, it does floating point division. So (6/4) evaluates to 1 while (6/4.0) evaluates to 1.5 -- the 6 is promoted to 6.0 before the division.
+ Addition
- Subtraction
/ Division
* Multiplication
% Remainder (mod)
Other Assignment Operators
In addition to the plain = operator, C includes many shorthand operators which represents variations on the basic =. For example += adds the right hand side to the left hand side. x = x + 10; can be reduced to x += 10;. This is most useful if x is a long expression such as the following, and in some cases it may run a little faster.
person->relatives.mom.numChildren += 2; // increase children by 2
Heres the list of assignment shorthand operators
+=, -= | | Increment or decrement by RHS |
*=, /= | | Multiply or divide by RHS |
%= | | Mod by RHS |
>>= | | Bitwise right shift by RHS (divide by power of 2) |
<<= | | Bitwise left shift RHS (multiply by power of 2) |
&=, |=, ^= | | Bitwise and, or, xor by RHS |
Stanford CS Education Library This [the above section] is document #101, Essential C, in the Stanford CS Education Library. This and other educational materials are available for free at http://cslibrary.stanford.edu/. This article is free to be used, reproduced, excerpted, retransmitted, or sold so long as this notice is clearly reproduced at its beginning. Copyright 1996-2003, Nick Parlante, nick.parlante@cs.stanford.edu.
end of Stanford C essentials
24 An assignment statement changes the value of a variable. :Ada-Europes Ada Reference Manual: Introduction: Language Summary See legal information
target := source;
Ada distinguishes between an assignment and an assignment statement.
In Ada assignment is indicated by the character pair colon and equal := and an assignment statement is terminated with a semicolon ;.
The EBNF definition of an Ada assignment statement is:
assignment_statement ::= variable_name := expression;
Only one variable may be on the left side of an assignment statement. The value assigned must be the same type as the variable and within the legal range for that variable.
The following material is from the unclassified Computer Programming Manual for the JOVIAL (J73) Language, RADC-TR-81-143, Final Technical Report of June 1981.
1.1.3 Calculations
In the simplest case, calculations is performed by an assignment
statement. An example is:
AVERAGE = (X1 + X2)/2;
The right-hand-side of this assigment is a formula; it forms the
sum of X1 and X2 and divides it by 2. The details of the
operation depend on how X1 and X2 are declared. If X1 and X2 are
declared float, the calculation is very likely to produce the
expected result. In contrast, if the X1 and X2 are declared
fixed, the scaling must be worked out by the programmer to make
sure the calculation will succeed. And if X1 and X2 are declared
character-string, the compiler will reject it because JOVIAL does
not automatically convert values into the types required by
operators.
In the example just given, the parenthesis show that the addition
is performed before the division. When parenthesis are not
given, JOVIAL recognizes the usual order of evaluation. Here is
an example:
POLY = BETA*X1**2 - GAMMA*X2 + DELTA;
JOVIAL applies its "rules of precedence" to the formula in this
assignment and thus interprets it as:
POLY = (((BETA*(X1**2)) - (GAMMA*X2)) + DELTA);
The complete precedence rules are given in Chapter 11.
Chapter 1 Introduction, page 6
The examples just given illustrate the use of formulas on the
right-hand side of an assignment statement. A formula can also
appear as part of the left-hand side of an assignment statement;
for example, as the subscript of an array In addition to their
important role in assignment statements, formulas can appear in
many other places in the language: as actual parameters of
functions and prcedures, as the condition in an if-statement,
and so on.
Since JOVIAL has quite a few kinds of values, it must have many
ways of converting one kind of value into another kind. In most
cases, you must explicitly indicate the conversion. An example
is:
ITEM MARK U 10;
ITEM TIME F;
...
MARK = (* U 16 *) (TIME);
The value of the floating item TIME is converted to a ten-bit
integer value before it is assigned to the ten-bit integer item
MARK. If you leave the conversion operator out of this
assignment, the compiler will report an error. The compiler
catches situations in which one type of value is uninetentionally
assigned to or combined with a different type of variable.
Chapter 1 Introduction, page 7
assembly language instructions
data movement
Data movement instructions move data from one location to another. The source and destination locations are determined by the addressing modes, and can be registers or memory. Some processors have different instructions for loading registers and storing to memory, while other processors have a single instruction with flexible addressing modes. Data movement instructions generally have the greatest options for addressing modes. Data movement instructions typically come in a variety of sizes. Data movement instructions destroy the previous contents of the destination. Data movement instructions typically set and clear processor flags. When the destination is a register and the data is smaller than the full register size, the data might be placed only in the low order bits (leaving high order bits unchanged), or might be zero- or sign-extended to fill the entire register (some processors only use one choice, others permit the programmer to choose how this is handled). Register to register operations can usually have the same source and destination register.
Earlier processors had different instructions and different names for different kinds of data movement, while most modern processors group data movement into a single symbolic name, with different kinds of data movement being indicated by address mode and size designation. A load instruction loads a register from memory. A store instruction stores the contents of a register into memory. A transfer instruction loads a register from another register. In processors that have separate names for different kinds of data moves, a memory to memory data move might be specially designated as a move instruction.
An exchange instruction exchanges the contents of two registers, two memory locations, or a register and a memory location (although some processors only have register-register exchanges or other limitations).
Some processors include versions of data movement instructions that can perform simple operations during the data move (such as compliment, negate, or absolute value).
Some processors include instructions that can save (to memory) or restore (from memory) a block of registers at one time (useful for implementing subroutines).
Some processors include instructions that can move a block of memory from one location to another at one time. If a processor includes string instructions, then there will usually be a string instruction that moves a string from one location in memory to another.
- MOVE Move Data; Motorola 680x0, Motorola 68300; move a byte (MOVE.B 8 bits), word (MOVE.W 16 bits), or longword (MOVE.L 32 bits) of data; memory to memory, memory to register, register to memory, or register to register; moves of byte and word data to registers leaves high order bits unchanged; sets or clears flags
- MOV Move Data; Intel 80x86; move a byte (8 bits), word (16 bits), or doubleword (32 bits) of data; memory to register, register to memory, or register to register (cannot move data from memory to memory or from segment register to segment register); does not affect flags
- MOV Move Data; DEC VAX; move a byte (MOVB 8 bits), word (MOVW 16 bits), longword (MOVL 32 bits), quadword (MOVQ 64 bits), octaword (MOVQ 128 bits), single precision floating (MOVF 32 bits), double precision floating (MOVD 64 bits), G floating (MOVG 64 bits), or H floating (MOVH 128 bits) of data; memory to memory, memory to register, register to memory, or register to register; moves of byte and word data to registers leaves high order bits unchanged; quadword, D float, and G float moves to or from registers are consecutive register pairs, octaword, and H float moves to or from registers are four consecutive registers; and sets or clears flags
- PUSH Push; Intel 80x86; decrement stack pointer and move a word (16 bits) or doubleword (32 bits) of data from memory or register (or byte of immediate data) onto stack; does not affect flags
- PUSHL Push Long; DEC VAX; decrement stack pointer (R14) and move a longword (32 bits) of data from memory or register onto stack; equivalent to MOVL src, -(SP), but shorter and executes faster; sets or clears flags
- POP Pop; Intel 80x86; move a word (16 bits) or doubleword (32 bits) of data from top of stack to register or memory and increment stack pointer; does not affect flags
- LR Load from Register; IBM 360/370; RR format; move a full word (32 bits) of data; register to register only; does not affect condition code
- L Load (from main storage); IBM 360/370; RX format; move a full word (32 bits) of data; main storage to register only; does not affect condition code
- LH Load Half-word; IBM 360/370; RX format; move a half-word (16 bits) of data; main storage to register only; does not affect condition code
- LDA Load A-register; MIX; move word or partial word field of data; main storage to accumulator only
- LDX Load X-register; MIX; move word or partial word field of data; main storage to extension register only
- LDi Load index-register; MIX; move word or partial word field of data; main storage to one of five index registers only
- ST Store (into main storage); IBM 360/370; RX format; move a full word (32 bits) of data; register to main storage only; does not affect condition code
- STH Store Half-word; IBM 360/370; RX format; move a half-word (16 bits) of data; register to main storage only; does not affect condition code
- STA Store A-register; MIX; move word or partial word field of data; accumulator to main storage only
- STX Store X-register; MIX; move word or partial word field of data; extension register to main storage only
- STi Store index-register; MIX; move word or partial word field of data; one of five index registers to main storage only
- MVI MoVe Immediate; IBM 360/370; SI format; move a character (8 bits) of data; immediate data to register only; does not affect condition code
- MOVEQ Move Quick; Motorola 680x0, Motorola 68300; moves byte (8 bits) of sign-extended data (32 bits) to a data register; sets or clears flags
- CLR Clear; Motorola 680x0, Motorola 68300; clears a register or contents of a memory location (.B 8, .W 16, or .L 32 bits) to zero; clears flags for memory and data registers, does not modify flags for address register
- CLR Clear; DEC VAX; clears a scalar quantity in register or memory to zero (CLRB 8 bits, CLRW 16 bits, CLRL 32 bits, CLRQ 64 bits, CLRO 128 bits, CLRF 32 bit float, or CLRD 64 bit float), an integer CLR will clear the same size floating point quantity because VAX floating point zero is represented as all zero bits; quadword and D float clears of registers are consecutive register pairs, octaword clears to registers are four consecutive registers; equivalent to MOVx #0, dst, but shorter and executes faster; sets or clears flags
- STZ Store Zero; MIX; move word or partial word field of data, store zero into designated word or field of word of memory
- EXG Exchange; Motorola 680x0, Motorola 68300; exchanges the data (32 bits) in two data registers; does not affect flags
- XCHG Exchange; Intel 80x86; exchanges the data (16 bits or 32 bits) in a register with the AX or EAX register or exchanges the data (8 bits, 16 bits, or 32 bits) in a register with the contents of an effective address (register or memory); LOCK prefix and LOCK# signal asserted in XCGHs involving memory; does not affect flags
- MOVSX Move with Sign Extension; Intel 80x86; moves data from a register or memory to a register, with a sign extension (conversion to larger binary integer: byte to word, byte to doubleword, or word to doubleword); does not affect flags
- MOVZX Move with Zero Extension; Intel 80x86; moves data from a register or memory to a register, with a zero extension (conversion to larger binary integer: byte to word, byte to doubleword, or word to doubleword); does not affect flags
- MOVZ Move Zero Extended; DEC VAX; moves an unsigned integer to a larger unsigned integer with zero extend, source and destination in register or memory (MOVZBW Byte to Word, MOVZBL Byte to Long, MOVZWL Word to Long); sets or clears flags
- MCOM Move Complemented; DEC VAX; moves the logical complement (ones complement) of an integer to register or memory (MCOMB 8 bits, MCOMW 16 bits, or MCOML 32 bits); sets or clears flags
- LCR Load Complement from Register; IBM 360/370; RR format; fetches a full word (32 bits) of data from one of 16 general purpose registers, complements the data, and stores a full word (32 bits) of data in one of 16 general purpose registers; register to register only; sets or clears flags
- LPR Load Positive from Register (absolute value); IBM 360/370; RR format; fetches a full word (32 bits) of data from one of 16 general purpose registers, creates the absolute value (positive) the data, and stores a full word (32 bits) of data in one of 16 general purpose registers; register to register only; sets or clears flags
- MNEG Move Negated; DEC VAX; moves the arithmetic negative of a scalar quantity to register or memory (MNEGB 8 bits, MNEGW 16 bits, MNEGL 32 bits, MNEGQ 64 bits, MNEGF 32 bit float, or MNEGD 64 bit float); if source is positive zero, result is also positive zero; sets or clears flags
- LNR Load Negative from Register (negative of absolute value); IBM 360/370; RR format; fetches a full word (32 bits) of data from one of 16 general purpose registers, creates the absolute value the data, complements (negative) the absolute value of the data, and stores a full word (32 bits) of data in one of 16 general purpose registers; register to register only; sets or clears flags
- LDAN Load A-register Negative; MIX; move word or partial word field of data, load sign field with opposite sign; main storage to accumulator only
- LDXN Load X-register Negative; MIX; move word or partial word field of data, load sign field with opposite sign; main storage to extension register only
- LDiN Load index-register Negative; MIX; move word or partial word field of data, load sign field with opposite sign; main storage to one of five index registers only
- STZ Store Zero; MIX; move word or partial word field of data, store zero into designated word or field of word of memory
- MVC MoVe Character; IBM 360/370; SS format; moves one to 256 characters (8 bits each) of data; main storage to main storage only; does not affect condition code
- MOVE Move (block); MIX; move the number of words specified by the F field from location M to the location specified by the contents of index register 1, incrementing the index register on each word moved
- MOVEM Move Multiple; Motorola 680x0, Motorola 68300; move contents of a list of registers to memory or restore from memory to a list of registers; does not affect condition code
- LM Load Multiple; IBM 360/370; RS format; moves a series of full words (32 bits) of data from memory to a series of general purpose registers; main storage to register only; does not affect condition code
- STM STore Multiple; IBM 360/370; RS format; moves contents of a series of general purpose registers to a series of full words (32 bits) in memory; register to main storage only; does not affect condition code
- PUSHA Push All Registers; Intel 80x86; move contents all 16-bit general purpose registers to memory pointed to by stack pointer (in the order AX, CX, DX, BX, original SP, BP, SI, and DI ); does not affect flags
- PUSHAD Push All Registers; Intel 80386; move contents all 32-bit general purpose registers to memory pointed to by stack pointer (in the order EAX, ECX, EDX, EBX, original ESP, EBP, ESI, and EDI ); does not affect flags
- POPA Pop All Registers; Intel 80x86; move memory pointed to by stack pointer to all 16-bit general purpose registers (except for SP); does not affect flags
- POPAD Pop All Registers; Intel 80386; move memory pointed to by stack pointer to all 32-bit general purpose registers (except for ESP); does not affect flags
- STJ Store jump-register; MIX; move word or partial word field of data; jump register to main storage only
- MOVEP Move Peripheral Data; Motorola 680x0, Motorola 68300; moves data (16 bits or 32 bits) from a data register to memory mapped peripherals or moves data from memory mapped peripherals to a data register, skipping every other byte
See also Data Movement Instructions in Assembly Language
Professors are invited to give feedback on both the proposed contents and the propsed order of this text book. Send commentary to Milo, PO Box 1361, Tustin, California, 92781, USA.
free music player coding example
Coding example: I am making heavily documented and explained open source code for a method to play music for free almost any song, no subscription fees, no download costs, no advertisements, all completely legal. This is done by building a front-end to YouTube (which checks the copyright permissions for you).
View music player in action: www.musicinpublic.com/.
Create your own copy from the original source code/ (presented for learning programming).
Because I no longer have the computer and software to make PDFs, the book is available as an HTML file, which you can convert into a PDF.
Names and logos of various OSs are trademarks of their respective owners.