Nothing Special   »   [go: up one dir, main page]

C Tutorial

Download as doc, pdf, or txt
Download as doc, pdf, or txt
You are on page 1of 134

Lesson 1: Transforming Numerical Systems

This is the first lesson I wrote. Its purpose is to introduce you to the world of
programming, showing you the way computers think or archive data. Please
be patient and read through the whole lesson carefully in order to fully
understand showed examples and calculations. I understand you can't wait to
start using the code, but believe me these general foundations are somehow
necessary to fully understand next tutorials and lessons I'll provide you with.
Take time, new lessons will be published in a time interval necessary for me
to compose them for your, and in the mean time you have time to carefully
run through previous like this one. Now we can begin...

Binary Numbers
Base system uses base B, and includes numbers 0, 1, 2, ... , B-1
For example in decimal system B=10, and numbers included are 0, 1, 2, ..., 8 &
9.
If the base B=2, then the system is binary, and its numbers are 0 & 1.
From English term BInary digiT, comes the name for lowest amount of
information BIT.
Example:
5710 = 5 * 101 + 7 * 100 = 1*25 + 1*24 + 1*23 + 0*22 + 0*21 + 1*20 = 1 1 1 0 0
12
Number 57 in decimal is shown by two numbers, while in binaries six figures
are necessary to show data. Binaries compared to other numbering systems,
logically use most amount of elements (data) to give us information. Number
of BITS used to write down a number is limited due to technical reasons.
Machines used to process and save binary information, are usually constructed
form electronic elements with 2 stable states (bistables), which are efficient and
cheap to produce.
Switching from decimal to binary numbers:
Binary number is made by leftovers we get from dividing (reading upwards)
57 : 2 = 28 1 1 1 0 0 1
1
28 : 2 = 14
0
14 : 2 = 7
0
7:2=3
1
3:2=1
1
1:2=0
1

Negative Binary Numbers

Operation 7 – 5 , using computer with 4 bit length registry will be processed


like

7 + (-5). Binary result of -5 can be achieved:

Positive Number 0 1 0 1

Complement till base -1 1 1 1 1

( one komplement) - 0 1 0 1
1010

Complement till base 1 0 1 0

(dual complement) + 0 0 0 1

1011

Proof that the result is - 5 Excluding operation 7 - 5

1 0 1 1 (-5)

+ 0 1 0 1 (+5)
---------------
0000

extra 1

0 1 1 1 ( 7)

+ 1 0 1 1 (-5)
---------------
0010

extra 1
If we have n=3 bit length registry, (first bit reserved for telling us if its –/+),
next numbers can be shown:
Decades Binaries
0 000
1 001
2 010
3 011

-4 100
-3 101
-2 110
-1 111

For n = 3 we get interval [-22, 22 - 1], in general [-2n-1, 2n-1 - 1].


For n = 8 we get interval [-27, 27-1], exact range [-128, 127].
Octal System
Base of the system is B=8 and numbers used are 0, 1, 2, 3, 4, 5, 6, 7.
This system is used for shorter description of binaries when its needed.
Example:
36-bit number 001 110 000 101 111 001 010 011 111 000 100 001
Octal equivalent 1 6 0 5 7 1 2 3 7 0 4 1
Hexadecimal System
Base of the system is B=16 and numbers used are 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A,
B, C, D, E, F. This system is used for shorter description of binaries when it’s
needed.
Example:
16-bit number 0111 1011 0011 1110
Hexadecimal equivalent. 7 B 3 E

Rational numbers
Rational numbers have binary “spot” which is similar to decimal spot used by
decimal numbers.
Example: conversion of rational number
5.75 10 = 5 * 100 + 7 * 10-1 + 5 * 10-2 =
= 1*22 + 0*21 + 1*20 + 1*2-1 + 1*2-2 = 1 0 1 . 1 1 2
Conversion of decimal number to binary number
1.25 = 1 + .25

.25 * 2 1 . 0 1

0.50

.5 * 2

1.0

Example: conversion of this decimal number - when conversed, it has infinite


number of fractions in its binary state
13.3 = 13 + 0.3

.3 * 2 1 1 0 1 . 0 1 0 0 1 1 0 0 1 ...
0.6

.6 * 2
1.2

.2 * 2
0.4

.4 * 2
0.8
.8 * 2
1.6

.6 * 2
1.2

....

Notice that finite decimal number is shown as infinite periodic binary number.
Binary Number is mounted with exponent of Base 2, in a way that a binary dot
is moved left or right, depending if exponent is positive or negative
Example: 1 . 1 1 * 22 = 1 1 1

Update - March, 8. 2006: Don't panic! if you didn't quite understand these
numerical systems, You can still read my additional lesson that should in-
depth cover this topic. There are many examples on numeric conversions
also. Soon, I'm going to post another lesson on calculations with binarie
numbers.

Lesson 2: IEEE Standards

Published Saturday, February 11, 2006 by Vurdlak | E-mail this post


This lesson is next and final step before we start to code. It is about decoding
numbers and saving them into computer using IEEE protocols for standard
and double precision. Normalization procedures are shown precisely and are
really easy to understand.

Display of Real Numbers by a computer


Standard precision: 32 bits (4 byte)
Double precision: 64 bits (8 byte)

Real Numbers of Standard Precision


Declaration in programming language C:
float
IEEE (Institute of Electrical and Electronics Engineers) standard 754 for
display of real numbers in standard precision:

P for sign ( P=1 negative, P=0 positive)

Characteristic binary exponent + 127 (to avoid display of negative


exponent)

Mantissa normalized (only one bit in front of a binary spot).

Example: display of decimal number 5.75


5.7510 = 101.112 * 20 = 1.01112 * 22
Because normalization of every binary number (except zero) displays
shape1.xxxxx, leading 1 is unnecessary. This is why the leading 1 isn’t saved
into computer and is referred as hidden bit. This advantage provides us one
extra bit of space, giving us higher precision possibility.
P =for sign = 0 (positive number)
Binary exponent = 2 K = 2 + 127 = 129 = (1000 0001)2
Mantissa (whole) 1.0111
Mantissa (without hidden bit) 0111
Resault: 0 10000001 01110000000000000000000
or 0100 0000 1011 1000 0000 0000 0000 0000
4 0 B 8 0 0 0 0 (hexadecimal)

Examples:
2 = 102 * 20 = 12 * 21 = 0100 0000 0000 0000 ... 0000 0000 = 4000 0000 hex
P = 0, K = 1 + 127 = 128 (10000000), M = (1.) 000 0000 ... 0000 0000
-2 = -102 * 20 = -12 * 21 = 1100 0000 0000 0000 ... 0000 0000 = C000 0000
hex
Equal to 2, but P = 1

4 = 1002 * 20 = 12 * 22 = 0100 0000 1000 0000 ... 0000 0000 = 4080 0000 hex
Equal Mantissa, BE = 2, K = 2 + 127 = 129 (10000001)

6 = 1102 * 20 = 1.12 * 22 = 0100 0000 1100 0000 ... 0000 0000 = 40C0 0000
hex

1 = 12 * 20 = 0011 1111 1000 0000 ... 0000 0000 = 3F80 0000 hex
K = 0 + 127 (01111111).
.75 = 0.112 * 20 = 1.12 * 2-1 = 0011 1111 0100 0000 ... 0000 0000 = 3F40 0000
hex

Special Case - 0:
Normalization of number 0 can’t produce shape 1.xxxxx
0 = 0 0000000 0000 ... like 1.02 * 2-127

Range and precision of Real Numbers:


In case of Real number of standard precision, characteristic (8 bits) can be
somewhere in interval [0,255].
K = 0 reserved to display zero
K = 255 reserved to display infinity
While BE = K - 127, BE can be created in interval [-126,127].

Smallest positive number different than zero which can be displayed:


1.02 * 2 -126 ~ 1.175494350822*10 -38

and the biggest is:


1.111111111111111111111112 * 2127 ~2128 = 3.402823669209*1038

Precision: 24 binary digits


224 ~ 10x 24 log 2 ~ x log 10 x ~ 24 log 2 ~ 7.224719895936
about first 7 digits are valid correct.

Display by numerical line:


Numerical mistake:
Not possible to use all bits while calculating:

Example: 0.000110 + 0.990010


0.000110 : (1.)101000110110111000101112 * 2-14
0.990010 : (1.)111110101110000101000112 * 2-1

While adding, binary spots must be one underneath the other:


#.000000000000011010001101 * 20 Only 11 of 24 bits!
+.111111010111000010100011 * 20
=.111111010111011100110000 * 20 = 0,990099906921410

Real numbers in double precise mode


Declaration in program language C:

double
P forsign ( P=1 negative, P=0 positive)

Characteristic binary exponent + 1023 (11 bits)

Mantissa normalized (52+1 bit).

Range:
K [0,2047].
K = 0 reserved for display of zero
K = 2047 reserved for display infinity
BE = K - 1023
BE [-1022,1023]

Smallest positive number different than zero which can be displayed:


1.02 * 2 -1022 ~ 2.225073858507*10 -308

and the biggest is:


1.1111.....1111112 * 21023 ~ 21024 = 1.797693134862316*10308

Correct: 53 binary numbers


253 ~ 10x 53 log 2 ~ x log 10 x ~ 53 log 2 ~ 15.95458977019
near to 16 first numbers are valid.

There is also:
long double 80 bits
Characteristic: 15 bits
Binary exponent: Characteristic - 16383

Real constants
1. 2.34 9e-8 8.345e+25 double
2f 2.34F -1.34e5f float
1.L 2.34L -2.5e-37L long double

Lesson 3: Data types in Registry

Published Saturday, February 11, 2006 by Vurdlak | E-mail this post


Here’s the third lesson you all waited for. It can also be considered as
prolonged intro on programming, however now I started giving you the code
and explaining its meaning. Please have patience and concentration, to fully
understande this lesson, since it covers explanations on most basic syntaxes
in C language.

Integer data type in C language:


Regarding precision, Integer type of data can be declared as short or long.
In C, there are no limitations on how short or long must be long, but some
rules apply:
 short can’t be longer than int
int can't be longer than long
Altogether regarding distance, we can declare: short =< int =< long
Integer type of data also includes: char (when representing numeral, and not
symbolic representation).

SIZE OF GENERAL DATA TYPES


Size of general types of data, more precise, amount of space which one
variable of general data type uses in memory isn’t fixed. It depends of
concrete implementation of translator program. Example of difference in
interpretation can be seen by translator programs made by Borland which
used 16 bits to save int variable, while Microsoft uses 32 bits to save
variable int in memory.

Size of general types of data (according to MSDN Library for MS


Visual C++ 6.0)

Type Size

char, unsigned char, signed char 1 octet

short, unsigned short 2 octet

int, unsigned int 4 octet


long, unsigned long 4 octet

float 4 octet

double 8 octet

long double 8 (10) octet

Dimensions of these types aren’t strictly regulated in C translator programs,


what leaves programmer (person) use of operator sizeof, which returns size
of wanted parameter in octets.
Operator sizeof can be also used to determine size of data types, along with
possibility to determine size of certain variable type!

Example:
int var;
printf("%d",sizeof(char)); // prints 1
printf("%d",sizeof(var)); // prints 4 (on MSVisualC++ 6.0)

Display of Integers with forsign and without it


Qualificator signed (with foresign) marks that varable can save positive and
negative number.
Variable declared as unsigned (without foresign) can save only positive
numbers, but it doubles our maximal positive number that can b saved
compared to signed.
Example:
Display hexadecimal content of variable short which consists of -7.
710 = 1112
0000000000000111
1111111111111000 (complement)
+1
1
1111111111111001
FFF9

Example:

Number 5 displayed in 16-bit registry:

0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 1

Number –5 displayed with method of double complement in 16-bit registry,


where leading 1, can be considered as number’s foresign (+/-) (1 means the
number is negative):
1 1 1 1 1 1 1 1 1 1 1 1 1 0 1 1

If we take the same flow of binary digits, and save them in an integer
variablewithout forsign, then the leading 1 is part of the number (NOT
FORESIGN IN THIS CASE). In this way number 65531 is shown:

1 1 1 1 1 1 1 1 1 1 1 1 1 0 1 1

Lesson 4: Casting data types

Published Saturday, February 11, 2006 by Vurdlak | E-mail this post


Someone's going to assume I'm workaholic since it has passed less then
twelve hours since my last programming post, but what the heck, I assume
you are willing to learn since you're here - so here's fourth lesson for all of
you. This lesson is about transformation (casting) of integers and real data
types, and explanations why this job is necessary in C language for compiler
to understand the syntax. It's a short one, but with compressed value.

DECLARATION OF INTEGER (int) TYPE:


CASTING DATA TYPES:
Result type of arithmetic phrase depends of operand types inside it. When a
phrase is consisted of various data types, result type is set by defined casting
rules. Rules for casting various data types in C language are oriented to
higher data type. There are two ways of casting data types in C:
automatic (implicit)
given (explicit)

Implicit Casting (automatic transformation) works in a way that a variable


(operand) of data type that is smaller in length (than data type of second
variable) (operand), transforming internally to variable of data type with
longer number length. It may sound mixed up, but here is an example:

short int -> int -> unsigned int ->long int -> unsigned long int -> float -
> double-> long double

This table shows standard automatic casting of one type of operand to


another type of operand in binary phrases (according to MSDN Library for
MS Visual C++ 6.0):
Operand Type Automatic Casting

One of operands Second operand transforms to long double.


is longdouble.

Previous rule doesn’t Second operand transforms to double.


apply, and one of
operands is double.

Previous rule doesn’t Second operand transforms to float.


apply, and one of
operands is float.

Previous rules don’t Integer casting is made by following rules:


apply, and none of
operands is real type • If one of operands is unsigned long, then
operand. another operand transforms to unsigned
long.

• If previous rule doesn’t apply, and if one of


operands is long, and other is unsignedint,
then both operands transform tounsigned
long.

• If previous rule doesn’t apply, and if one of


operands is long, then another operand is
transformed to long.

• If previous rule doesn’t apply, and if one of


operands is unsigned int, then another
operand transforms to unsigned int.

• If previous rules do not apply, then both


operands transform to int.
Important: rules for integer and real data type casting can differ from one
translator programs to another.

Exmple:
int a;
unsigned long b;
float f, g;
double d;
g = a + f; // a transforms to float
d = a + b; // a and b transform to unsigned long, adding
// is produced in unsigned long domain and then
// the result type unsigned long is transformed
// to double

Example:
long lm = LONG_MAX, l; // LONG_MAX = 2147483647
unsigned long um = ULONG_MAX; // ULONG_MAX = 4294967295
float f;
l = lm + 1; // result: -2147483648 (fill over to neg. field)
f = lm + 1; // result: -2147483648.000000 (result is made
// in long domain)
l = um + 1; // result: 0 (fill over)
f = um + 1; // result: 0.000000 (result is made in
// unsigned long domain)

Explicit Casting (given transformation) of data types has higher priority


then automatic transformation. General declaration
of explicit (given) cast (cast operator):
(data_type) operand
Operand can be variable or phrase.

Example:
a = (int) c;
b = (double)d + c;

Lesson 5: Operators and Integer operations

Published Sunday, February 12, 2006 by Vurdlak | E-mail this post


Again, I'm working as fast as I can on development of new C material, but
also am cautious to avoid mistakes. If you encounter any, feel free to add
comment so I can remove them. Here's fifth lesson on operators, their
priority and laws of casting (transforming) data types in automatic (implicit)
or given (explicit) way. Hope you have no problem following my text, I
include as much examples I can to help you visualize and understand C++
programming language, eventhough these are C foundations for now. Here
we go...

DIVIDING INTEGERS
It’s important to notice that sometimes we get “unwanted” results when
dividing whole numbers. For example if we want to assign ½ to real variable
a, assigning won’t work as we would like it; the result wouldn’t be 0.5:

a = 1 / 2;

In this expression, right side of equation consist of two whole number


operands, thus the dividing result will be whole number. Result will be 0
(with remainder 1).
To avoid this kind of unwanted results, its smart to use explicit casting
(given transformation) of data types mentioned in Lesson 4 (its enough to
use it only once on one operand) or to set constants so at least one operand is
real type:

a = (float) 1 / 2; or
a = 1. / 2; or
a = 1 / 2.;

Important:
First case shows us way of using explicit casting (it could also be used on
second operand), and second and third example shows us possibility of
adding spot, which declares constant as real number. This makes our result
to be processed in real domain.
OPERATORS PRIORITY

1. * / %
2. + -

If the expression has more operators of equal priority, they process in a


priority from left to right, one after another. Expressions inside ( ) have
highest priority.

Example:
What’s the result of following expression?
5 + 10 / 3 * ( 8 – 6 )
5 + 10 / 3 * 2
5+3*2
5+6
11

Example:
What’s the result?
a) 9 / 4
Result: 2 (dividing of whole numbers)

b) 9 % 4
Result: 1 (% means remainder form division of whole numbers: 9 : 4 = 2 +
remainder 1)
Example:
What’s the result we get assigned to following operands i, x, c

int i;
double x, c, d;
after these phrases:
d = 6.0;
i = (int)(d + 1.73);
x = i / 2;
c = (double)i / 2;

Result:
i = 7, x = 3, c = 3.5

OPERATORS REFLECTION ON BITS

& AND
| OR
^ XOR
<< SHIFT LEFT
>> SHIFT RIGHT
~ NOT
Operators &, |, ^ are binary operators (defined above two bits). Operator ~
isunary operator (defined above single bit).

Operators reflecting on bit operands (b1 and b2 represent bits):

b1 b2 b1 & b2 b1 | b2 b1 ^ b2

0 0 0 0 0

0 1 0 1 1

1 0 0 1 1

1 1 1 1 0

b1 ~b1

0 1

1 0

Example:
Calculate phrases: 3 & 5, 3 | 5, 3 ^ 5, ~3

0000 0011 (3)


&0000 0101 (5)
-------------------
0000 0001 (1)

0000 0011 (3)


| 0000 0101 (5)
-------------------
0000 0111 (7)

0000 0011 (3)


^ 0000 0101 (5)
-------------------
0000 0110 (6)

~ 0000 0011 (3)


--------------------
1111 1100 (252 or –4)

Operators <<>> are used to reposition all the variables content bits, left or
right. Repositioning all the bits one place left is the same as multiplying the
variables content by 2 (x2), while repositioning one place right is the same as
dividing content with 2 (/2).
Electronic computers in general have repositioning instruction implemented in
their registry and in this way multiplying or dividing using number proportional
with 2, is many times faster than classical multiplying or dividing.
Number of places this operand repositions the content, is given with parameter.

Example:
Calculate these phrases: 2<<1 , and 37 >>2

0000 0010 (2)


After reposition one place left
0000 0100 (4)

0010 0101 (37)


After reposition two places right (37>>2), result is variable divided with 4
(whole number part):
0000 1001 (9)

Important:
In case data is saved in a single octet, without the bit reserved for foresign
(+/-), calculate 128 <<1

1000 0000 (128)


After reposition one place left:
0000 0000 (0)
In case data is saved in single octet, including the bit reserved for foresign (+/-),
calculate 64 <<1
0100 0000 (64)
After reposition one place left:
1000 0000 (-128)

Lesson 6: ASCII code and character variables

Published Wednesday, February 15, 2006 by Vurdlak | E-mail this post

This lesson, as can be presumed from its title, will teach you what is
ASCII code, how does it affect programmer’s variables and what
is the difference between number and numerical figure. This one's
easy... Hope you still haven't pulled back; just when I hit you in
the face with hardcore code in next few lessons, don't say I caught
you off guard :) Developing your own program, even as simple as
calculator can give you nice, productive feeling.

DISPLAY OF SYMBOLS IN PROGRAM LANGUAGE C

a) Archiving small Integer numbers

b) Archiving letters, punctuation signs, special symbols

Character type variable (char) is capable of saving alphanumeric


data, and it uses 1 octet (byte) for doing it. Alphanumeric symbols
are: letters, numbers and special symbols that can be input via
keyboard. Character type variables can have for-sign (signed
char) or have no for-sign (unsigned char).
Declaration in program language C, and numerical range that is
covered by following data types:

char [-128, 127]

unsigned char [0,255]

Universal standard: 7-bit ASCII code (American Standard Code


for Information Interchange)

In program language C, all the characters are saved as a number


sequence that represent ASCII value (code) of the preferred
character
Important ASCII values:

0 – character NULL ('\0')

32 – space (' ')

48 – 57 – numbers '0'-'9'

65 – 90 – capital letters 'A' to 'Z'

97 –122 – small letters 'a' to 'z' (97 – 65 = 32 – difference between


capital and small letter!)

CHARACTER CONSTANTS

Character constants are given inside (' ') singular quotation


marks, NOT (“ “):

char a;
a = 'X';
Example:

Variable c is character type. Value of letter A is assigned to it in a


few different ways:

c = 'A';

c = 65; // ASCII code of letter 'A' is

//6510 = 4116 = 1018

c='\x41'; // hexadecimal constants begin

//with \x

c='\0101'; // octal constants begin with s \0

Example:

Variable c is character type. Use it to assign values of single


quotation mark (') and character \

c='\''; // special characters inside

// single quotation mark must have prefix \

c='\\';

When character type is used to save number figures, we must be


careful and pay attention that char variable saves ASCII value of
that particular figure, not the actual value, in short:

char a;
a = '1'; // equal to: a = 49;

Variable a contains numerical value 49, what is ASCII value of


character '1'. However if we want to get numerical value of a
character, then we take out 48 from value that is saved. 48
presents ASCII figure. Value 48 presents ASCII figure '0'.
It's important to notice that some numerical figures presented as
ASCII characters, don't represent binary expressions of the same
figures shown as integers.

Example:

Variable a, (type char) is holding figure '7'. Transform this value


to a number!

Binary expression of variable a is 0011 0111 (ASCII value 5510).

char a = '7';

short int number;

number = a – 48; or

number = a – '0'; or

number = a & 0x0f;

0011 0111 (5510)


0000 1111 (0x0f)
---------
0000 0111 (710)

Example:
char c ='A';

What’s the result of following executions?

printf ("%c", c); // result A


printf ("%d", c); // result 65
printf ("%c", c + 32); // result a
printf ("%d", 'B' – 'A')); // result 1

Resulting symbols are displayed on your monitor (printf).

Example:

Given variables a and b (type char) consist of figures ('0'-'9').


Write down an expression that will calculate number that is equal
to sum of these numerical figures (for example, result of '5' and
'6' should be 11.)

char a,b;

int i;

i = a - '0' + b - '0';

or

i = a + b – 2 * '0';

or

i = a + b - 96; // 2 * 48

Lesson 7: Assigning, Comparison, IF Conditions

Published Friday, February 17, 2006 by Vurdlak | E-mail this post


Seventh lesson on Assigning Operators, Comparison Operators, If
conditional and coding is up! Remember to Bookmark (CTRL + D) my
website if you find it helpful. Also please point on errors and mistakes you
encounter reading my tutorials. Remember, English is not my native
language so here and then it can be problematic to understand a word or two.

ASSIGNIN OPERATOR

Assigning Operator we use in C programming is =. This operator is


different than conditional operator used to compare two values (==).
Assigning Operator assigns value on right side (r-value) to operand on left
side (l-value). Difference between l-value and r-value is that l-value operand
has to have well defined address even after assigning value to it.

Example:

We can put:

a = b + 3;

but we can’t:

b + 3 = a;

C language also allows multiple assigning:

Example:
a = b = c = 0;

All three variables are initialized to 0 value. Priority of assigning is from


right to left as if we wrote in it this way:
a = (b = (c = 0));
First we assign 0 to variable c, then to value of this whole expression (c = 0)
is assigned value 0; then value of this expression is assigned to variable b,
then this whole expression is valued 0, and assigned to variable a.

a = b = c + 3;

Is this possible?

a = b + 3 = c = d * 3; // NO IT ISN’T!!! (b+3 isn’t l-value)

In programming we often calculate new value of variables based on value of


the other variables. This is why C also allows shorter equations for
assigning..

Some of the operators used for shorter assigning: +=, -= , *= , /= , %=

Example:

Phrase:

i = i + 5;
can also be written this way:

i += 5;

Phrase:

i = i * a;

can also be written this way:

i *= a;

OPERATORS FOR HIGHERING AND LOWERING PARTICULAR


VALUE

C language has two operators that are able to resize variable’s value to
higher or lower value. Cause of their existence is to provide more efficient
executions (there are some special processor instructions that are capable
executing this operations very fast).

• prefixing (operator in front of variable)


++a; --a;

• post fixing (operator after variable)


a++; a--;

Using ++ or – operators with simple numeric types (variants of char, int and
real types), resizes to higher or lower value just by one. These operators are
useful when working with index fields, pointers and counters inside a loop.
It is advised to use prefix operators, because they are more efficient (postfix
operators create a temporary variable where they assign previous operand’s
value, which is used through the whole expression).

Example:

a = 5;
b = ++a * 2;
c = b++;

After execution of these orders, a gets value 6, b gets value 13, and c gets
value 12

Its better to avoid dual use of these operators. Example:

a = fn1( i++ ) + fn2( i++);

In this expression we’re not sure which function will be processed first..

COMPARISON OPERATORS

Comparison operators are used when we need to compare data. We can


compare constants, variables and phrases. Program language C has
following comparison operators:
Comparison operator as a result gives TRUTH (value different than 0) or
FALSE (zero). C language doesn’t support logical type of data; instead
logical values are shown with help of numerical values.

CONDITION PHRASE IF

Comparison operators are usually included in condition phrases. Depending


on a comparison operator’s result, the phrase gets executed or doesn’t. C
language supports three shapes of conditional IF phrases.

1. Simple selection

2. Two-sided selection

3. Multi-sided selection

Example:

What’s the result we get printed on screen, after this block of orders is
executed?

1.) a = 25 and b = 4.
2.) a = 0, b = 0

if (a = b)

printf ("Values of both variables are equal\n");

else
printf ("Values of both variables are different\n");

Result:

1) When a = 25 , b = 4, after assigning a = b, a gets value 4 and the whole


expression gets value 4. Block of orders after if is executed only if statement
is TRUE (different than zero, our expression is 4) it will be printed: "Values
of both variables are equal".

2) After assigning whole expressions equals zero, so "Values of both


variables are different" is going to be written:

Question: What would happen in both situations, if the condition were (a ==


b)?

Answer: Since we have logical comparison operator, (not assigning), the


result is printed:

1) "Values of both variables are different"


2) "Values of both variables are equal"

Important:

if (a = b)

is the same as:

a = b; if (a)

Example:

Write your own program block that will add int variables a and b if the value
of char variable c is equal to '+'. If the value of c is '-', then it will subtract
mentioned variables. If the value of c is some other sign, then program must
return error sentence. Result must be assigned to variable r.

int a,b,r;
char c;

if( c == '+' )
r = a + b;
else if( c == '-')
r = a - b;
else
printf("Error – wrong operation");
Example:

Write your own program that will calculate crossing point of two lengths in
a real number axis (assuming that the first length is left on the axis and the
second right on the axis).

Important:

Pay attention in following example that "else" belongs to second "if


condition", and not the first one. If else condition is needed to be assigned to
first (outer) if condition, then whole block of orders after first if order must
be placed inside brackets { }.

int a1, a2, b1, b2; // lengths [a1, a2] and [b1, b2]
int r1, r2; // result [r1, r2]

if( a2 > b1 ) /* means they are crossing each other */


if( a1 > b1 ) /* means whole length A is inside length B */
{
r1 = a1;
r2 = a2;
}
else
{
r1 = b1;
r2 = a2;
}

Lesson 9: Two-sided and Multi-sided Selections


Published Tuesday, February 21, 2006 by Vurdlak | E-mail this post
This lesson is examples only! Think you will specially love this one since it
will bring you much knowledge in spite of small example blocks length. My
recommendation is first to try and understand these executions, then try
reading the task again and try solving it on your own… you will learn faster
in this way. On the other hand, if you’re lazy but still want to learn, just read
it twice or three times.

OPERATORS PRIORITY

What’s the value of variable d after executing following program block:

short int a=4, b=2, c=8, d;


d = a < 10 && 2 * b < c;

Result:

d = ( a < 10 ) && ( ( 2 * b ) < c )


d = 1 && (4<8)
d = 1 && 1
d=1

What will be printed on your screen after executing this block?

int a = 5, b = -1, c = 0;
c = (a = c && b) ? a = b: ++c;
printf("a = %d, b = %d, c = %d: \n", a, b, c);

Result:

a = 0 , b = -1 , c = 1
TWOSIDED SELECTION

Example:

Write your own program that calculates and prints absolute value of given
number:

#include<stdio.h>

void main(){

int number,abs;

printf("Input number: ");


scanf("%d",&number); /*can also be written: */
if (number < 0) { /*if (number < 0) */

abs = -number; /* abs = -number; */

else { /*else */

abs = number; /* abs = number; */

printf("Absolute value of given number %d is:


%d\n", number, abs);
}
Example:

Program calculates circle’s area with radius given from user:

#include <stdio.h>
#define PI 3.141592

void main(){

float radius, area;

printf("Input circle’s radius: ");


scanf("%f",&radius);
if (radius <= 0) {

printf("You have entered false radius!\n");


}
else {

area=radius*radius*PI;
printf("Circle’s area is: %f\n", area);
}
}
What will be printed if someone enters -10 in "Input circle’s radius:"

You have entered false radius!


Circle’s area is: x.xxxxx (depending on content of memory locations
assigned to variable area)

1. How would you modify upper program so that calculation-result


message appears only if the program really calculated area of the
circle?

2. How would you avoid unexpected-unknown result?

1. Execution printf("Circle’s area is: %f\n", area); would be written under


else part:

if (radius <= 0) {

printf("You have entered false radius!\n");


}

else {

area=radius*radius*PI;
printf("Circle’s area is: %f\n", area);
}

2. I would initialize variable area.


float radius, area = 0;

Example:

Write your own program which reads two given numbers, tests if the first
number is dividable with second one (with no remain left); and prints
suitable message. Second number must be different than 0 (why?).

#include <stdio.h>

void main(){

int a,b;

printf("Give a and b:");


scanf("%d %d", &a, &b);
if (b != 0) {

if (a % b == 0) {

printf("%d is dividable with %d\n", a, b);

}
else {

printf("%d isn’t dividable with %d\n", a, b);


}
}
}
Alternative approach:

if (b != 0) {

printf("%d %s dividable with %d\n",


a, a % b ? "isn’t" : "is", b);
}

MULTISIDED SELECTION

Example:

Oven is capable of producing working temperature in interval [50°C-80°C].


Write your own program that tests if the oven temperature given through
keyboard is in previously mentioned interval; and prints suitable message.

#inclde <stdio.h>
#define lower 50.0
#define upper 80.0
void main(){

float temp;

printf("\n Give oven temperature: ");


scanf("%f",&temp);
if (temp < lower) {
printf("Temperature has fallen below interval!\n");
} else if (temp > upper) {
printf("Temperature has risen above interval!\n");
} else {
printf("Temperature of oven is OK\n");
}
}

Lesson 10: Program Iterations

Published Thursday, February 23, 2006 by Vurdlak | E-mail this post


Today’s lecture is also examples mostly, but this time I’ll introduce you to
iterations and you will see why these program lines are common in every
programmer’s code. Just don’t be confused when you see i= i++ (this really
bugged me when I was first introduced to world of programming). How the
heck can i be equal to i+1 ? You have to think outside of the box this time,
and forget regular math.

Program Iterations

Program iterations are used to process certain program’s block, multiple


number of times. Number of repeats (iterations) can be, or don’t have to be
previously known. We have following iterations that:

• test condition before starting iteration (while, for)

• test condition at the end (do-while)

Iterations that tests iteration condition at the beginning


Example:

Write your own program that will read given positive-whole numbers, until
number zero is given. Then it will print which given number was the
smallest. The program must ignore given negative numbers (given =
keyboard inputted).

Warning: While searching for smallest (biggest) filed member or flow, we


use following algorithm:

1. first member in field is declared smallest and it’s value is assigned to


temp variable, which presents current minimum.

2. we search through other field members and if one of them is smaller


then our current minimum, we update our temp variable to show new
current minimum.

3. after we processed the whole field, temp variable now stores the real
minimum member of field.

Example:

flow: 5, 6, 3, 9, 4, 7, 2, -1, 5.

#include <stdio.h>
void main() {

int min, x = 0;

while(x <= 0){

printf("Input number : ");


scanf("%d", &x);
min = x; // we assume first given number is the smallest

while (x != 0) {

printf("Input number : ");


scanf("%d", &x);
if(x > 0 && x < min )
min = x;

printf("Smallest given number is: %d\n", min);

Alternative approach (to avoid double storing)

#include <stdio.h>

void main() {

int min=0, x=1;


// in first iteration x=1

while (x != 0) {

printf("Input number : ");


scanf("%d", &x); //after first iteration x becomes != 1
if (x > 0) {

if ((min==0) || (x < min)) min = x;

}
}

printf("Smallest given number is: %d\n", min);

Example:

Program reads positive-whole numbers until their sum reaches value bigger
than approved range short int allows. Program also prints last valid sum.

#include <stdio.h>

void main() {

short int x, sum = 0, end = 0;

while (!end) {
printf("Input number : ");
scanf("%d", &x);

if ((signed short)(sum+x) >= sum) { //why cast?

sum += x;

} else {

end = 1;

}
}

printf("Sum: %d\n", sum);

Example of programs testing:

Input number : 30000


Input number : 10
Input number : 10000
Sum: 30010

Is the number of iterations in this program block previously known?

Example:

Program prints first 100 numbers that are dividable with 7:


#include <stdio.h>

void main() {

int i=0, n=0;

while (n < 100) {

if (i % 7 == 0) {

printf ("%d\n", i);


n++;

i++;

}
}

Example:

Program reads positive-whole number and calculates range of following


numbers in this way:
• if the given number is even, then divides it with 2

if the given number is odd, then multiplies it with 3 and adds 1


The procedure is repeated until given number becomes 1. Program prints


current value in every step. Program also prints number of calculations
above processed number.
#include <stdio.h>

void main() {

int number, nrSteps = 0;

printf("Give positive number:");


scanf("%d", &number);
while (number > 1) {

++ nrSteps;
if (number % 2){

number = number * 3 + 1;

else {

number /= 2;

printf ("In %d. step, number = %d \n", nrSteps, number);

printf ("All together %d steps. \n", nrSteps);

}
Give positive number: 9
In 1. step, number = 28
In 2. step, number = 14
In 3. step, number = 7
In 4. step, number = 22
In 5. step, number = 11
In 6. step, number = 34
In 7. step, number = 17
In 8. step, number = 52
In 9. step, number = 26
In 10. step, number = 13
In 11. step, number = 40
In 12. step, number = 20
In 13. step, number = 10
In 14. step, number = 5
In 15. step, number = 16
In 16. step, number = 8
In 17. step, number = 4
In 18. step, number = 2
In 19. step, number = 1
All together 19 steps.

Lesson 11: Infinite and Finite Loops

Published Sunday, February 26, 2006 by Vurdlak | E-mail this post


Seems to me that submitting new lessons every two days became a rutine
lately. Let’s hope it stays that way. Today I posted new lesson which will
put some light on programming loops - you surely have heard about those.
So from now on, when you watch Futurama and hear Beneder blabring
something about being stuck in an infinite loop, you’ll understand his
problem in details: from one – to zero. Hehe, let’s start...
Iteration with previously known number of repeats.

Syntax:

for (expression1; expression2; expression3) {


.
.
.
}

• expression1 is an expression which will be executed only once, before


entering into the first iteration. It’s most commonly used for counters
initialization. If more then one expression is needed in this field, they
are separated by comma.

• expression2 is calculated as logical condition (0 - false, !=0 - true),


and the iteration is executed number of times expression2 is true.
Testing of condition is done before any iteration is processed.

• expression3 is executed after each iteration (executed loop). It’s most


common use is to increase counter’s value. If more then one
expression is needed to be executed, they are separated by comma.

• either one of expressions (expression1; expression2; expression3) can


be left out. If expression 2 is left out, loop is executed as if logical
value of the expression were TRUE.

Common use:
for (i = start; i <= end; i = i + k) {
.
.
.
}

Example of “for” loop with 2 counters:

for (hi = 100, lo = 0; hi >= lo; hi--, lo++) {


.
.
.
}

Example:

Write your own program that will calculate arithmetic middle of n given
numbers.

#include <stdio.h>

void main() {

int i, n, sum, x;
float arit_midd;

printf("For how many numbers do you wish to calc. their arithmetic


middle : ");
scanf("%d", &n );
sum = 0;
for(i=0; i<n; i++) {

printf("Give %d. number : ", i);


scanf("%d", &x);
sum += x;

arit_midd = (float) sum / n;


printf("Arithmetic middle of scanned numbers is %f\n", arit_midd);

Example:

Write your own program which will print real numbers from 0 till n, with
step of 0.1

#include <stdio.h>

void main() {

int n;
float i;

printf("Until which number do you wish report to be printed on


screen :");
scanf("%d", &n );

for( i=0; i<=n; i=i+0.1 ) {


printf("%f\n",i);

}
}

Example:

Write your own program which will print numbers dividable with 7, 13 and
19, and lower than given number n. Numbers must be printed from biggest
to the lowest one.

#include <stdio.h>

void main() {

int i, n;

printf("Give number n : ");


scanf("%d", &n );

for( i=n; i > 0; i-- ) {

if ( i % 7 == 0 ) || ( i % 13 == 0 ) || (i % 19 == 0) {

printf(" %d \n", i);

}
}
}
Warning:

for(;;); // infinite loop

or

for(;;){

//block of orders

Block of orders inside the body of loop is executed infinite number of times
if that block doesn’t consist of: breaking order (break), order for escaping
the function (return), program finish function call (exit) or goto order.

Common Mistakes:
Iteration (loop) which tests condition at the end.

Syntax:

do {
.
.
.
} while (expression);

• loop is executed while condition is true, for example this is different


in Pascal, where loop is executed until expression becomes true
(means it keeps executing while condition is false)

• loop will be executed minimum once (first test of condition comes


after first run through the loop)

Example in C:

do {
.
.
.
} while (x < y);

Same example in Pascal:

repeat
.
.
.
until ( x >= y )

Example

Write your own program that reads numbers from interval [-100, 100] or
[800, 1000]. Program has to print how much of these numbers were positive,
how much of them were negative and how much times 0 encountered.

Program has to be written using “do – while” loop.

#include <stdio.h>

void main(){

int number;
int nrPositive=0, nrNegative=0, nrZero=0;
printf("Give in numbers: ");

do {

scanf("%d", &number);
if (number >=-100 && number <=100 || number >=800 && number
<=1000) {

if (!number) nrZero ++;


else if (number >0) nrPositive ++;
else nrNegative ++;

}while (number >=-100 && number <=100 || number >=800 && number
<=1000);

printf("Number of positive number %d, number of negative numbers


%d, number of
zeroes %d\n", nrPositive, nrNegative, nrZero);

Example

Following program block:

k=0;
i=7;
lab:
k=k+i*2;
i=i-2;
printf ("%d\n", k);
if (i >= -7) goto lab;

should be replaced with following loop:

1. Loop that tests condition at start

2. Loop that tests condition at the end

3. Loop that has previously known number of repeats


Solved:

1.)

k=0;
i=7;
while (i>=-7) {

k=k+i*2;
i=i-2;
printf ("%d\n", k);
}

2.)

k=0;
i=7;
do {

k=k+i*2;
i=i-2;
printf ("%d\n", k);

} while(i >= -7);

3.)

for (i = 7, k = 0; i >= -7; i-=2){

k = k + i * 2;
printf ("%d\n", k);
}

Warning: if it’s initialized that i < -7, 1. and 3. loop won’t be


executed neither once, but 2. loop will be executed once.

Advantage of “for” loop: it’s starting counter’s initialization,


testing of condition and counters step, all are placed in one place
in programmer’s code. This can be really practical.

Lesson 12: Switch-Case, Break; and Continue;

Published Thursday, March 02, 2006 by Vurdlak | E-mail this post


New lesson is up. I’ve composed this one, based on common examples
where controls: break; and continue; are used. Another explanation on
branching - using “switch – case” order is provided. Enjoy it! Hope you’ve
noticed by now I also added some appendixes (more to be added soon); and
for some time now, I post regular News regarding C++ Maniac homepage
development. You can find these links in my sidebar.

Loop flow controls: break; and continue;

C uses two different orders to control loop’s flow


• break – escapes from the nearest outer loop

• continue – inside “while” and “do” loop: switches program execution


to test condition, inside “for” loop: switches program execution to
“for” loop step and then to condition test (also applies for nearest
outer loop) - this can sound little messy, so better check the examples

Example:

Write your own program that tests if the given number is prime number.

#include <stdio.h>
#include <math.h>

void main() {

int i, n, prime=1; // prime is true

printf("Input natural number :");


scanf("%d", &n);

for( i=2; i<= n-1; i++) {

if( n % i == 0 ) { // also possible to state if(!(n % i))

prime =0; // prime is now false


break;

}
}

if( prime )

printf("%d is prime number !\n", n);

else
printf("%d isn’t prime number!\n", n);

Possible algorithm enhancements (decreasing number of loop’s


iterations/repeats):

• It is enough to loop n/2 times, better, only till square root(n) (C


function sqrt(n))

• Test if the number is dividable with 2, and if it isn’t, test inside loop if
the number is dividable with odd numbers bigger than 2

Example:

Write your own program that reads integers given by keyboard and applies
following rule above them: if the given number is smaller than zero,
program should print error message and stop reading numbers. If the given
number is bigger than 100, it should be skipped and program should read
another number. All other numbers should be red and printed. Program must
stop reading numbers when 0 or error shows up.

#include <stdio.h>

void main() {

int x;
do {

printf ("Input number :\n");


scanf("%d", &x );
if (x < 0) {

printf("Not allowed value\n");


break;
/* escapes the loop */
}

if (x > 100) {

printf("Skipping the value\n");


continue;
/* jumps to second iteration */

printf ("Given number is : %d", x);

} while (x != 0);
}

Branching condition order switch – case

Syntax:

switch( expression ){

case const_expression1: orders1;


[case const_expression2: orders2;]
.
.
.
[default : oredersN;]

• used instead of multisided if selection

• pay attention: if the keyword break isn’t stated inside case block;
program continues to next case block in the list!

Example

Program reads student’s grade given from keyboard (from 1 to 5) and prints
it’s description.

#include <stdio.h>

void main() {

int grade;
printf ("Input grade :");
scanf("%d", & grade);

switch (grade) {

case 1:
printf("Fall (F)\n");break;
case 2:
printf("Bad (D)\n");break;
case 3:
printf("Good (C)\n");break;
case 4:
printf("Very Good (B)\n");break;
case 5:
printf("Excellent (A)\n");break;
default:
printf("You have inputted false grade\n");
break; // break isn’t necessary here
}
}

Pay Attention:

If break; was to be left-out from every case block, for given grade 3
(example), the result would be false and following:

Good
Very Good
Excellent
You have inputted false grade

Pay Attention:

If the “default” block is last block in your switch order, then it isn’t
necessary to state break next to it.

Pay Attention:

Consequence of falling through case labels in lack of break order is that the
same collection of orders is executed for more different case labels. Better
explained, this allows the following code

switch (letter) {

case 'a': NrOfVowels++; break;


case 'e': NrOfVowels ++; break;
case 'i' : NrOfVowels ++; break;
case 'o': NrOfVowels ++; break;
case 'u': NrOfVowels ++; break;
default : NrOfOthers++; break;
}

also to be written more shortly, in this way:

switch (letter) {

case 'a':
case 'e':
case 'i' :
case 'o':
case 'u': NrOfVowels ++; break;
default : NrOfOthers++; break;
}
Lesson 13: Hello World! - A Classic -

Published Saturday, March 04, 2006 by Vurdlak | E-mail this post


This is a true classic. I covered "Hello World!" example in this lesson, which
is the one everybody encounters when learning to program – It's just sooner
or later. Well, in my lessons –later-. Most of other tutorials start with this
example, but I think I'm on the right path of introducing you to it only now.
Not much of a new stuff covered here. More like repeating and affirmation.

Loops

Example:

What is the printed result of following program block?

i = 1;
while (i < 5) {

if (i==3) {

printf (“\n Hello world %d.x!”, i);


continue;

} else if (i==4) {

printf (“\n Goodbye %d.x!”, i);


continue;

}
i++;
}
Result:

Hello world 3.x!


Hello world 3.x!
...
...
… and so on for infinite number of times. Even after value 3 is reached,
orders under i==3 are executed. Because of “continue” command, i doesn’t
increase, but the program branches on conditional phrase (i < 5).

Example:

Write your own program block that prints multiplying table of numbers up
to 100.

/*1*/ int main(void) {


/*2*/ int i,j;
/*3*/
/*4*/ for (i = 1; i <= 10; ++i) {
/*5*/ for (j = 1; j <= 10; ++j)
/*6*/ printf("%3d",i*j);
/*7*/ printf("\n");
/*8*/ }
/*9*/}
By adding single line of code, we accomplish that new table is made from
even numbers only:

/*6*/ if ( (i%2!=0) &&amp; (j%2!=0) ) continue; // both odd numbers

Same thing:

/*6*/ if ( (i%2==0) || (j%2==0) ) // at least one number is even

Example:

Write your own program block that prints first N Fibonacci numbers. N is
given by keyboard. Algorithm to calculate Fibonacci Numbers:

Fibonacci(n) = Fibonacci(n-1) + Fibonacci(n-2)


Fibonacci(0) = Fibonacci(1) = 1

1, 1, 2, 3, 5, 8, 13, 21,...

#include <stdio.h>

int main () {

int N, i, f0 = 1, f1 = 1,f = 1;
printf ("\n Input amount of Fibonacci Numbers (N) : \n");
scanf ("%d",&N);
for (i = 0; i <= N; i++) {
if (i > 1) {

f = f1 + f0;
f0 = f1;
f1 = f;
}
printf ("Fibonnaci (%d) = %d \n", i , f);
}
return 0;
}

Example:

Write your own program which reads 2 real numbers and numeric operation
executed above them (+, -, /, *) (all given by keyboard). If the given
operation is different than allowed, program asks for new operation input.

#include <stdio.h>

int main(void) {

float a,b, result;


char operation;
int repeatOperationInput = 1;

printf("Input two numbers: ");


scanf("%f, %f", &a, &b);

do {
printf("Input operation: ");
operation = getche();
printf("\n");
repeatOperationInput = 0;

switch(operation) {

case '+': result = a + b; break;


case '-': result = a - b; break;
case '*': result = a * b; break;
case '/':
if (b == 0) {
printf("Dividing by 0 isn’t allowed.\n");
}
else {
result = a / b;
}
break;
default:
repeatOperationInput = 1;
}
} while (repeatOperationInput);

printf("%f %c %f = %f\n", a, operation, b, result);

// What if b == 0?

}
Lesson 14: Arrays

Published Sunday, March 05, 2006 by Vurdlak | E-mail this post


In C language arrays are very popular. They can be found in almost any
program code and are pretty helpful and easy to understand. To understand
them, just visualize a sequence of numbers and try assigning them to only
one declaration. It can be done if the declaration is properly stated as an
array including index brackets (example int MySequence[20]).

Arrays

Array is data structure used to share multiple data elements under a single
name declaration. It’s important that every single element of data, we wish
to assign to array, belongs to the same data type. Array’s elements are easily
accessed – we use index; a number that must be nonnegative integer
(constant, variable, integer expression). Element’s index is a number
between 0 and the number of elements minus one, including. In short: Index
( [0, NrOfElements – 1].

Declaration of an array:

data_type array[index];

Array’s definition in C:

int x[20] – array consisted of 20 integer numbers


char symbols[2] – array consisted of 2 characters
float sequence[MAX] – MAX is constant
Assigning element’s values definition:

int array[ ] = {1, 2, 3};


array[0] = 1
array[1] = 2
array[2] = 3

int array [4] = {1, 2};


array[0] = 1
array[1] = 2
array[2] = 0
array[3] = 0

Accessing array’s elements:

x[0] – first element of an array


sequence[i] – i. element of an array, 0 <= i <= NrOfElements – 1
sequence[MAX – 1] – last element of an array

Common Wrong access to array’s elements:

int array[10] = {0};


int x = sequence[10];

float a = 1.;
int x = array[a];
int a = 1, b = 0, c = 1;
int x = array[(a && b) - c];
Example:

Write your own program that asks user to input sequence of numbers,
afterwards it calculates arithmetic middle of the given sequence. Program
also prints numbers smaller than arithmetic middle, and afterwards prints
numbers bigger than arithmetic middle.

#include <stdio.h>
#define DIMENSION 10

int main(void) {

int i;
float sum = 0., arit_midd = 0., sequence[DIMENSION]={0};

for (i = 0; i < DIMENSION; i++) {

printf("Input number: ");


scanf("%f",&sequence[i]);
sum += sequence[i];

arit_midd = sum / DIMENSION;


printf("Arithmetic middle of the sequence is %6.2f.\n", arit_midd);
for (i = 0; i < DIMENSION; i++) {

if (sequence[i] < arit_midd) {

printf("%6.2f is smaller than arithmetic middle.\n", sequence[i]);

}
}

for (i = 0; i < DIMENSION; i++) {

if (sequence[i] > arit_midd) {

printf("%6.2f is bigger than arithmetic middle.\n", sequence[i]);

}
}

// What happens if the number is equal to arithmetic middle?

Example:

Write your own program that asks for input of sequence of numbers. After
the program reads given numbers, it divides every number with the biggest
sequence element and shows them in a way relative to the biggest element.

#include <stdio.h>
#define DIMENSION 10

int main(void) {

int i;
float max, array[DIMENSION];

for (i = 0; i < DIMENSION; i++) {


printf("array[%d] = ", i);
scanf("%f",& array[i]);
if (i == 0) {

max = array[i];

}
if (max < array[i]) {

max = array[i];

}
}

printf("Biggest element in array is %f.\n\n", max);


for (i = 0; i < DIMENSION; i++) {

array[i] /= max;
printf("array[%d] = %f\n", i, array[i]);

}
}

Example:

Compose your own program that reads given natural numbers that belong in
[10, 99] interval and counts how many times each number showed up.
Program stops reading numbers when element that doesn’t belong to interval
is given. Afterwards, program prints each number from the interval that has
showed at least once, and number of times it has really been given.
#include <stdio.h>

#define LL 10 /* lower limit of the interval */


#define UL 99 /* upper limit of the interval */

int main(void) {

int number, i;
int counter[UL – LL + 1] = { 0 };

do {

printf("\nInput number from interval [%d, %d]: ", LL, UL);


scanf("%d", &number);
if (number >= LL && number <= UL) {

counter[number - LL]++;

} while (number >= LL && number <= UL);

for (i = DG; i <= UL; i++) {

if (counter[i - LL] > 0) {

printf("\nNumber %d showed up %d times", i, counter [i - LL]);

}
}
}
Lesson 15: Matrixes and 2D Arrays

Published Friday, March 10, 2006 by Vurdlak | E-mail this post


There was a slight pause in my C++ Maniac programming tutorial, due to
me answering some of your C & C++ lesson-related questions. You can find
some explanations on previous programming materials in my sidebar now,
along with other new C & C++ stuff. It seems to me finally, after all
troubleshoots are answered (or are they?!), we can bravely continue. This
15th lesson is about matrixes and two-dimensional C++ arrays. Although
this one may look significantly more complicated, if you read through it
carefully, you will conquer programming matrixes with no problem – I
promise you that.

Declaration of a 2D array in C language:

int x[3][2] - matrix 3X2 (3 rows, 2 columns), elements: integers


char myascii[2][4] - array of characters (2 rows & 4 columns)
float sequence[MAXROW][MAXCOL] - MAXROW X MAXCOL matrix

Example of declaration with initialization:

int array[3][3] = {1, 2, 3, 4, 5};


array[0][0] = 1
array[0][1] = 2
array[0][2] = 3
array[1][0] = 4
array[1][1] = 5
array[1][2] = 0 // even though nowhere stated
array[2][0] = 0
array[2][1] = 0
array[2][2] = 0
char cmaniac[7] = {'C', 'M', 'A', 'N', 'I', 'A', 'C'}

/* array of characters */

int y[3][4] = { {1, 2, 3},


{4, 5, 6},
{7, 8, 9} };

y[0][0]= 1 y[0][1]= 2 y[0][2]= 3 y[0][3]= 0


y[1][0]= 4 y[1][1]= 5 y[1][2]= 6 y[1][3]= 0
y[2][0]= 7 y[2][1]= 8 y[2][2]= 9 y[2][3]= 0

Declaration of multidimensional array:

int x[3][2][4] 3D array of integer numbers


float x[3][2][4][1] 4D array of real numbers
Example:

Write your own C program that reads through real matrix, 10x10
dimensioned and finds the smallest element in main diagonal and smallest
element in secondary diagonal.

#include <stdio.h>

#define NR_ROW 10
#define NR_COL 10

int main(void) {

int i, j;
float mat[NR_ROW][NR_COL], min_maindg, min_secdg;

printf("Input matrix elements :");


for (i = 0; i < NR_ROW; i++) {
for (j = 0; j < NR_COL; j++) {

printf("\nInput element [%d][%d] : ", i, j);


scanf("%f", &mat[i][j]);

}
}

min_maindg = mat[0][0];
//min el. is mat(0,0), this is why loop starts from 1

for (i = 1; i < NR_ROW; i++) {

if (mat[i][i] < min_maindg) {

min_maindg = mat[i][i];

}
}

min_secdg = mat[0][NR_COL -1];


for (i = 1; i < NR_ROW; i++) {

if (mat[i][NR_COL-i-1] < min_secdg) {

min_secdg = mat[i][NR_COL-i-1];

}
}

printf("\nSmallest el. in main diagonal is: %f",


min_maindg);
printf("\nSmallest el. in second diagonal is: %f",
min_secdg);
}

Shorter version – single run through the matrix:

#include <stdio.h>

#define NR_ROW 10
#define NR_COL 10

int main(void) {

int i, j;
float mat[NR_ROW][NR_COL], min_maindg, min_secdg;

printf("\nInput matrix elements :\n");


for (i = 0; i < NR_ROW; i++) {
for (j = 0; j < NR_COL; j++) {

printf("\nInput element [%d][%d] : ", i, j);


scanf("%f", &mat[i][j]);

if (i == 0 && j == 0) {

min_maindg = mat[i][j];

}
if (i == 0 && j == NR_COL - 1) {

min_secdg = mat[i][j];

}
if (i == j) {
if (mat[i][j] < min_maindg) {

min_maindg = mat[i][j];

}
}
if (i == NR_COL - 1 - j) {
if (mat[i][j] < min_secdg) {

min_secdg = mat[i][j];
}
}
}
}
printf("\nSmallest element in main diagonal is : %f",
min_maindg);
printf("\nSmallest element in second diagonal is : %f",
min_secdg);
}

Example:

Write your own C program that transposes matrix. Program stores given
matrix dimensions and every single matrix element must be given.
Transposed matrix is the one with rows and columns switched.

#include <stdio.h>

#define MAX_ROW 50
#define MAX_COL 50

int main(void) {

int i, j, m, n, temp;
int mat[MAX_ROW][MAX_COL];

// variable dim is set to smaller value of defined


// maximal number of rows and columns
int dim = (MAX_ROW < MAX_COL)? MAX_ROW : MAX_COL;

// storing matrix size

do {

printf("Input number of rows < %d :", dim);


scanf("%d", &m);
printf("Input number of columns < %d:", dim);
scanf("%d", &n);

} while (m < 1 || m > dim || n < 1 || n > dim);

// storing matrix elements

printf("\nInput of matrix elements :\n");


for (i = 0; i < m; i++) {
for (j = 0; j < n; j++) {

printf("Input element [%d][%d] : ", i, j);


scanf("%d", &mat[i][j]);

}
}

// printing matrix before transposing

printf("\n\nMatrix before transposing:\n");


for (i = 0; i < m; i++) {
for (j = 0; j < n; j++) {

printf("%3d", mat[i][j]);

}
printf("\n");
}

// transposing

for ( i=0; i<m; ++i ) {


// looping must start from i+1 !!
for ( j=i+1; j<n; ++j ) {

temp = mat[i][j];
mat[i][j] = mat[j][i];
mat[j][i] = temp;
}
}

// print after transposing


// number of rows becomes number of columns ...

printf("\nMatrix after transposing:\n");


for (i = 0; i < n; i++) {
for (j = 0; j < m; j++) {

printf("%3d", mat[i][j]);
}
printf("\n");
}
} // main

Example of program’s execution:

Input number of rows < 50: 3


Input number of columns < 50: 2
Input of matrix elements :
Input element [0][0] : 1
Input element [0][1] : 2
Input element [1][0] : 3
Input element [1][1] : 4
Input element [2][0] : 5
Input element [2][1] : 6

Matrix before transposing:

1 2
3 4
5 6

Matrix after transposing:

1 3 5
2 4 6
Example:

Write your own C program that stores real matrix whose dimensions are
10x10, and finds the sum of elements from every column and product of
elements from every row. Program prints the smallest sum (including parent
column’s index), and biggest product (including parent row’s index). Sums
and products should be stored in one-dimensional arrays.

#include <stdio.h>

#define NR_ROW 10
#define NR_COL 10

int main(void) {

int i, j;
int min_sum_ind, max_prod_ind;
float mat[NR_ROW][NR_COL];
float sum[NR_COL], prod[NR_ROW];

/*1.variant of input and calculating sums & products*/

for (i = 0; i < NR_ROW; i++) {


for (j = 0; j < NR_COL; j++) {

printf("\nInput element[%d][%d] : ", i, j);


scanf("%f", &mat[i][j]);
}
}

for (j = 0; j < NR_COL; j++) {


sum[j] = 0;

for (i = 0; i < NR_ROW; i++) {

sum[j] += mat[i][j];

}
}

for (i = 0; i < NR_ROW; i++) {

prod[i] = 1;

for (j = 0; j < NR_COL; j++) {

prod[i] *= mat[i][j];
}
}

/*end of input, and sums & products calculation*/

/* finding column’s index for smallest sum */

min_sum_ind = 0;
for (j = 1; j < NR_COL; j++) {
if (sum[j] < sum[min_sum_ind]) {

min_sum_ind = j;
}
}

/* finding row’s index for biggest product */


max_prod_ind = 0;
for (i = 1; i < NR_ROW; i++) {
if (prod[i] > prod[max_prod_ind]) {

max_prod_ind = i;
}
}

printf("\nSmallest sum: %f, parent index: %d\n",


sum[min_sum_ind], min_sum_ind);
printf("\nBiggest product: %f, parent index: %d\n",
prod[max_prod_ind], max_prod_ind);
}

Shorter variant for storing elements and calculating sums & products:

/*2.variant of input and calculating sums & products*/

for (i = 0; i < NR_ROW; i++) {

prod[i] = 1;
for (j = 0; j < NR_COL; j++) {

printf("\nInput element [%d][%d] : ", i, j);


scanf("%f", &mat[i][j]);
prod[i] *= mat[i][j];
if (i == 0) {

sum[j] = 0;

}
sum[j] += mat[i][j];

}
}

/* end of input, and sums & products calculation */

Lesson 16: Functions in C

Published Sunday, March 12, 2006 by Vurdlak | E-mail this post


Functions are essential part of code in C and C++ language, so be sure to
carefully read this lesson. You’ll notice there’s nothing to be afraid of – they
are really easy to understand, and sometimes, can lighten up our program
code significantly. In a way, they remind us of our main program. Functions
usually return value that we use in our main block, but sometimes they
return nothing. Either way, they do their task: like printing on screen or
calculating equations. C++ Maniac presents you another interesting tutorial!

Example:

Write your own function that calculates arithmetic middle of three real
numbers. Write additional main program that stores given three numbers and
calls on your previous function, and then prints calculated arithmetic middle.

#include <stdio.h>

float arit_midd( float a, float b, float c ){

float ar;
ar = (a + b + c) / 3;
return ar; // How many values “return” may return?

int main(void) {

float x, y, z, midd;
printf("\nInput three real numbers : ");
scanf("%f %f %f", &x, &y, &z );
midd = arit_midd(x,y,z);
printf("\nArithmetic middle : %f", midd);

Example:

What will be printed after execution of a program that calls on a function?

void twotimes(int x) {

printf ("\nF:Argument before change took place %d",x);


x *= 2;
printf ("\nF:Argument after tempering with it %d",x);

int main(void) {

int number=10;
printf ("\nM:Number before function-call %d",number);
twotimes(number);
printf("\nM:Number after function-call is %d",number);

Result on-screen:

M:Number before function-call 10


F:Argument before change took place 10
F:Argument after tempering with it 20
M:Number after function-call 10

Change inside a function wasn’t saved after execution and return to


main program! Why?

int twotimes(int x){

printf ("\nF:Argument before change took place %d",x);


x *= 2;
printf ("\nF:Argument after tempering with it %d",x);
return x;

int main(void) {

int number=10;
printf ("\nM:Number before function-call %d",number);
broj = twotimes(number);
printf("\nM:Number after function-call %d",number);
}

Result on-screen:

M:Number before function-call 10


F:Argument before change took place 10
F:Argument after tempering with it 20
M:Number after function-call 20

Example:

Compose a function that calculates value of a sinus func. as sum of n


elements. Function’s argument is given in radians. Func. sinus is defined as:

#include <stdio.h>
#include <math.h>

//realization with use of no additional functions

float sinus(float x, int n){


int i, forsign;
float sum, element, fakt, xpot;
sum = 0.0;
xpot = x;
fakt = 1.0;
forsign = 1;

for( i=1; i<=n; i++ ) {

element = forsign * xpot / fakt;


forsign *= -1;
xpot *= x*x;
fakt *= (2*i) * (2*i+1);
sum += element;

return sum;

//realization with help of additional functions

long fakt( int n ){

int i;
long f=1;
for( i=1; i<=n; i++ ) {
f *= i; }
return f;

}
float sinus(float x, int n){

int i, forsign;
float sum, element; sum = 0.0; forsign = 1;
for( i=1; i<=n; i++ ) {

element = forsign * pow(x,2*i-1) / fakt(2*i-1);


forsign *= -1;
sum += element;

return sum;

Lesson 17: Pointers in C

Published Wednesday, March 15, 2006 by Vurdlak | E-mail this post


After three days of waiting, C++ Maniac brings you another interesting
lesson. This one is labeled no. 17, and I think moment has come when I can
proudly say we have crossed a half-way of my complete C Tutorial; at least
first part of it, “C Programming In General”. This Lesson is about Pointers
and their useful implementation in Your future C programs. Let’s start…

Important:
Examples are translated using Microsoft Visual C++ compiler.

Example:

What will be printed after execution of a following program block?

int a = 5; //a address:1245052, value:5

int *b; //a address:1245052, value:5


//b address:1245048, value:?

b = &a; //a address:1245052, value:5


//b address:1245048, value:1245052

*b = 6; //a address:1245052, value:6


//b address:1245048, value:1245052

printf("a = %d *b = %d\n", a, *b);


printf("a = %d b = %ld\n", a, b);
printf("&a = %ld &b = %ld\n", &a, &b);

Result:

a = 6 *b = 6
a = 6 b = 1245052
&a = 1245052 &b = 1245048
Important:

Value that is pointed by variable b is on the same address (b = &a) as the


value assigned to variable a.

What would happen if we left out this line: b = &a; ?

Result:

Before assigning value to it, pointer b points to undefined address. This


makes it possible for program to store value 6 to an address previously
reserved for some other variable or code. This would result in an unexpected
behavior or cause an error in program’s execution (because of unauthorized
access to memory’s section).

Typical Mistakes:

scanf(“%d", n);
printf(“%d", &n);

Connection between Pointers and Arrays:

Any declared array’s name can also be used as a pointer. Any pointer can
also be used as an array.

What will be printed as a result of following program block?


int x[] = {0, 1, 2}; //x[0] address:1245044, value:0
//x[1] address:1245048, value:1
//x[2] address:1245052, value:2

printf("&x[0] = %ld x[0] = %d\n", &x[0], x[0]); // 1


printf("&x[1] = %ld x[1] = %d\n", &x[1], x[1]); // 2
printf("&x[2] = %ld x[2] = %d\n", &x[2], x[2]); // 3

Result:

&x[0] = 1245044 x[0] = 0


&x[1] = 1245048 x[1] = 1
&x[2] = 1245052 x[2] = 2

Important:

Printings in an upper block could’ve been substituted with following lines:

printf("x = %ld *x = %d\n", x, *x); // 1


printf("(x + 1) = %ld *(x+1) = %d\n", x + 1, *(x+1)); // 2
printf("(x + 2) = %ld *(x+2) = %d\n", x + 2, *(x+2)); // 3

because these following lines are equivalent:

*x <=> x[0] x <=> &x[0]


*(x+1) <=> x[1] x+1 <=> &x[1]
*(x+2) <=> x[2] x+2 <=> &x[2]
Array’s name (in upper example: x) represents pointer to null member of an
array. Notation x + 1 represents pointer to first member of an array, whose
distance from null member is: 1 * sizeof(int). In a same way, x +
2 represents pointer to second member of an array, whose distance from null
member is:
2 * sizeof(int).

Array’s Name as Pointer’s Constant:

When compiling this program block:

int a[10], b[10];


a = b;

error is reported. Array’s name (a) is representing pointer’s constant in this


example, and because of that we aren’t able to modify this pointer’s value.

Connection between Pointers and Array’s:

Assigning array’s address to pointer (which is equivalent to assigning


address of first array’s element to pointer) can be executed in two ways:

int *p, a[10];


p = a; // first solution
p = &a[0]; // second solution
Pointer’s Arithmetic:

What will be printed after execution of a following C program block?

int x[] = {1, 2, 3, 4}; //x[0] address:1245040, value:1


//x[1] address:1245044, value:2
//x[2] address:1245048, value:3
//x[3] address:1245052, value:4

int *p = &x[2]; //p address:1245036, value:1245048

int *q = &x[1]; //q address:1245032, value:1245044

int *r = ++q;
//r address:1245028, value:1245048
//q address:1245032, value:1245048

printf("(p + 1) = %d *(p + 1) = %d\n", (p + 1), *(p + 1));


printf("(p - 1) = %d *(p - 1) = %d\n", (p - 1), *(p - 1));
printf("q = %d *q = %d\n", q, *q);
printf("r = %d *r = %d\n", r, *r);

Result:
(p + 1) = 1245052 *(p + 1) = 4
(p - 1) = 1245044 *(p - 1) = 2
q = 1245048 *q = 3
r = 1245048 *r = 3

Lesson 18: Pointers and Stacks in C

Published Sunday, March 19, 2006 by Vurdlak | E-mail this post


Today's lesson goes more into details about pointers and their usage as
function's arguments. Additional tutorial about stacks in C and C++ is
provided. Be sure to read this lesson carefully in order to understand it, since
pointers are most important part of C programming language.

Transferring Argument’s Address into a Function (call by reference)

Write your own function that changes polar coordinates into Cartesian
coordinates, and show how this function is called upon from main program.

#include <math.h>

void cart(float r, float fi, float *x, float *y) {

*x = r*cos(fi); // x address:1244956,value:1245052
//*x address:1245052,value:1.755165

*y = r*sin(fi); // y address:1244960,value:1245048
//*y address:1245048,value:0.958851
}

Main program slice:

float x, y; // x address:1245052,value:?
// y address:1245048,value:?

float fi = 0.5, r = 2; //fi address:1245044,value:0.5


// r address:1245040,value:2

cart(r, fi, &x, &y);

printf("x=%f y=%f",x,y);

// x address:1245052, value:1.755165
// y address:1245048, value:0.958851

Question:

What would happen if the function looked like this?

void cart(float r, float fi, float *x, float *y) {

x = 10000;
*x = r * sin(fi);
*y = r * cos(fi);

}
Important:

Function is able to return single value through its “return” order. In order to
return more values (in this case x & y), we can return them through
arguments (Call by Reference).

Example:

Write your own function that returns numerator and denominator of a


fraction. This fraction is a sum of two fractions, whose two numerators and
two denominators are given by user. Function also shortens the fraction if
possible, before returning values. Augends numerators and denominators are
integers.

(Fraction example: 5/9, Numerator: 5, Denominator: 9)

void addFractions(int nrator1,int denom1,


int nrator2,int denom2,
int *nratorSum,int *denomSum) {

int min, i;

*nratorSum = nrator1*denom2+denom1*nrator2;
*denomSum = denom1*denom2;

min=(*nratorSum<*denomSum) ? *nratorSum : *denomSum;

//testing if numerator and denominator


//are multiples:

if((*nratorSum % min == 0)&&(*denomSum % min==0)){


*nratorSum /= min;
*denomSum /= min;

} else {

//tests if numerator and denominator are


//dividable with same number

i = min / 2;
while ( i >= 2) {

if ((*nratorSum%i == 0)&&(*denomSum%i == 0))

*nratorSum /= i;
*denomSum /= i;

--i;
}
}
}

Main program’s slice (calls function addFractions):

int nrator1, denom1, nrator2, denom2,


int nratorSum, denomSum;

...

addFractions(nrator1, denom1, nrator2,


denom2, &nratorSum, &denomSum);

Function that finds biggest element in real number’s array


Why is flow’s length “length” transferred as function’s argument?

float max(int length, float *p) {

// OR: float max(int length, float p[]) {

float res; int i;

res = p[0];
for (i = 1; i < length; i++)
if (p[i] > res)
res = p[i];
return res;

Same problem - solved using pointer’s arithmetic:

float max(int length, float *p) {

float res;
int i;

res = *p;
p++;
for (i = 1; i < length; i++, p++)
if (*p > res)
res = *p;
return res;

}
Important:

Pointer p stores address of the first array element. However, if we shift


pointerp inside the function, address of the first array’s element won’t be
changed, neither will influent our main program (that calls the function).

Example:

Exam’s results are transferred into a function in a way of array composed of


integers (integers represent grades). This array (flow), is consisted of grades
1, 2, 3, 4 and 5. Number of array’s elements is nrGrades. Write your own
function that returns most common grade.

int commonGrade(int *flow, int nrGrades) {

int grade[5] = {0}, commonGrade = 0, i;

for(i = 0; i < nrGrades; i++){

grade[flow[i] -1]++;

for(i = 1; i < 5; i++){

if(grade[i] > grade[commonGrade]) {

commonGrade = i;
}
}
return commonGrade + 1;
}

Example:

Write your own function that shifts array p (given, integer type) for a
number of places. Array p is consisted of N number of elements, and will be
shifted left for negative value, or shifted right for positive value
(adjustment < N). Empty places are filled with zeroes.

Example of shifting:

shift = 2 and array[10 40 50 60 12]:


Before shifting: [10 40 50 60 12]
Shifted array: [ 0 0 10 40 50]

Solution:

void shiftArray(int *p, int N, int shift) {

int i;

// if shifting right

if (shift > 0 && shift < N) {

for (i = N - 1 - shift; i >= 0; i --)


p[i + shift] = p[i];
for (i = shift - 1; i >= 0; i --)
p[i] = 0;
}

// if shifting left

else if (shift < 0 && -shift < N) {

shift = -shift;
for (i = 0; i <= N - 1 - shift; i++)
p[i] = p[i + shift];
for (i = N - shift; i < N; i++)
p[i] = 0;
}
}

Stack Data Storage with Function call

Every new element is stored on top of the stack. However, compilers often
tend to assign lower address to stack’s top, then to stack’s bottom. This
results data being stored downwards (from bottom of the stack
to lowermemory addresses).

Following data is stored to a stack (from higher addresses to lower ones):

- function’s arguments (highest address is assigned to ultimately-right


placed argument)
- returning address
- local variables (highest address is assigned to first declared variable)
Important:

While transferring data to a stack, frames of the stack will be ignored in this
tutorial (processor registers). However, some compilers also tend to store
these to a stack.

For how many bytes does the stack maximally increase, while executing this
block:

...
...
y= f1(10);
...

if the following functions are defined:

long f2(float a, float b) {

return a + b;

int f1(char x) {

int i = 4, y;
y = x + 1;
return i * f2(x, y);

}
f1 call: f2 call: STACK’S TOP
(lower addresses)
returning address 2
10 (float) ^
11 (float) / \
11 (int) 11 (int) / \
4 (int) 4 (int) / __ \
returning address 1 returning address 1
10 (char) 10 (char) STACK’S
BOTTOM
(higher addresses)

Returning address is data type long.

By calling function f2, stack has increased to its maximal size:

sizeof(char)
+ sizeof(returning address 1)
+ 2 * sizeof(int)
+ 2 * sizeof(float)
+ sizeof(returning address 2)

--------------

= 25 byte
Lesson 19: C Programming Examples

Published Thursday, March 23, 2006 by Vurdlak | E-mail this post


I’ve based this lesson on a single program example. This part of C
programming tutorial has dual purpose: firstly to teach you how to apply
previously learned C/C++ knowledge, second: to show you how pointers,
arrays, functions and matrixes can be combined together in one single
program.

Example:

Maximal number of rows and columns matrix can have is predefined. Write
your own main program which reads given number of matrix’s rows and
columns, and additionally reads matrix’s given elements. Main program
prints:

1. Matrix’s elements sum (calls upon a function that calculates elements


sum)

2. Maximal value in every row of a matrix (calls upon a function that


finds the biggest element in a flow)
Matrix mat is declared in a way of two dimensional array (2D array):

float mat[MAXROW][MAXCOL];

Variables nrRow and nrCol store matrix’s dimensions provided by user.


The image below shows you this in a visual way. Click on the image to
enlarge it.

Memory of a computer allocates MAXROW * MAXCOL * sizeof(float)


byte.Matrix’s rows follow one after another, in a way where every next row
is placed right after the previous one; and so on. Picture below describes this
perfectly. Click on the image to enlarge it.
Generally speaking, for mat[i][j] – number of elements from the beginning
of an array is: i * MAXCOL + j

#include <stdio.h>
#define MAXROW 100
#define MAXCOL 100

float max( int len, float *p ) {


// OR: float max( int len, float p[] )

float res;
int i;

printf("\nIn function max :");


printf("\nRow’s beginning address
in memory : %ld", p);
res = p[0];
for( i=1; i<len; i++ )
if( p[i] > res )
res = p[i];
return res;
}

float sumEl(int nrRow,int nrCol,


int maxCol,float *mat) {

int i, j;
float sum;

printf("\nIn function sumEl:");


printf("\nMatrix’s beginning address
in memory: %ld", mat);
printf("\nBegin. of 2nd row’s addr.
in mem.: %ld", &mat[maxCol]);
printf("\nBegin. of 3rd row’s addr.
in mem.: %ld", &mat[2* maxCol]);

sum = 0.0;
for( i=0; i<nrRow; i++ )
for( j=0; j<nrCol; j++ )
sum += mat[i*maxCol + j];
// or: sum += *(mat + i*maxCol + j)

return sum;
}

int main(void) {

int row, col, i, j;


float add, maxRow, mat[MAXROW][MAXCOL];

printf("\nInput nr. of rows and columns:");


scanf("%d %d", &row, &col );

printf("\nIn function main");


printf("\nMatrix’s beginning address
in memory: %ld", mat);
printf("\nBegin. of 2nd row’s
addr.: %ld\n\n", &mat[1][0]);
printf("\nBegin. of 3rd row’s
addr.: %ld\n\n", &mat[2][0]);
for( i=0; i<row; i++ )
for( j=0; j<col; j++ ) {
printf("Input element[%d,%d]:",i,j);
scanf("%f", &mat[i][j] );
}
//calculates elements sum in matrix

add=sumEl(row,col,MAXCOL,(float *) mat);
printf("\n\nSum of matrix
elements is %f", add );

//prints maximal value of every mat. row

for(i=0;i<row;i++) {
maxRow = max(col, &mat[i][0]);
// or: max(col, mat+i*MAXCOL)
printf("\nBiggest element in
row %d is %f\n",i,maxRow);
}
}

Example of program’s execution:

Input nr. of rows and columns: 3 2

In function main :
Matrix’s beginning address in memory : 1205032
Begin. of 2nd row’s addr. : 1205432
Begin. of 3rd row’s addr. : 1205832

3rd:
1205432 = 125032 + 1 * MAXCOL * sizeof(float)
= 125032 + 400;
1205832 = 125032 + 2 * MAXCOL * sizeof(float)
= 125032 + 800;

Input element [0,0]: 2


Input element [0,1]: 3
Input element [1,0]: 4
Input element [1,1]: 3
Input element [2,0]: 1
Input element [2,1]: 5

In function sumEl:
Matrix’s beginning address in memory: 1205032
Begin. of 2nd row’s addr. in mem.: 1205432
Begin. of 3rd row’s addr. in mem.: 1205832

Sum of matrix elements is 18.000000


In function max:
Row’s beginning address in memory: 1205032
Biggest element in row 0 is 3.000000

In function max:
Row’s beginning address in memory: 1205432
Biggest element in row 1 is 4.000000

In function max:
Row’s beginning address in memory: 1205832
Biggest element in row 2 is 5.000000

Example:

Write your own C function which returns flow of matrix row’s maximal
values.

void maxFlow(float *mat,int nrRow,int nrCol,


int maxCol,float *flow) {

//OR: void maxFlow(float mat[], int nrRow,


int nrCol,int maxCol,float flow[])

int i, j;
for (i = 0; i < nrRow; i++) {
flow[i] = mat[i * maxCol];
for(j = 1; j < nrCol; j++)
if (mat[i*maxCol+j] > flow[i])
flow[i]=mat[i*maxCol+j];
}
}

Numerical Systems

Published Wednesday, March 08, 2006 by Vurdlak | E-mail this post


Our society uses numerical system with base 10. Simple explanation
why this system is used - simply because people have ten fingers,
thus this is the easiest way for us to calculate numbers. If things
were gone different, and something had messed up primordial
soup -> developing Homo sapiens with eight fingers, it would be
more likely we would use octal numeric system in present time.
Infinite number of numerical systems exist, but following are most
commonly used...

Decimal System:

Base: 10
Digits: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9

Octal System:

Base: 8
Digits: 0, 1, 2, 3, 4, 5, 6, 7
Example: 27 (decimal) = 33 8 (octal)

Hexadecimal (hex) System:

Base: 16
Digits: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E, F
Example: 27 (decimal) = 1B 16 (hex)

Binary System:
Base: 2
Digits: 0, 1
Example: 27 (decimal) = 11011 2 (binary)

Numeric Transformations

Published Wednesday, March 08, 2006 by Vurdlak | E-mail this post


General Method of Transforming Numbers

Number we want to transform uses base X: we would like to transform this


number into new one, that uses Y base. In this case we will use method of
continuous dividing and multiplying (dividing numbers left of comma (,)
with Y and multiplying numbers on the right side of comma, by Y - rational
numbers). This method is best understood looking at these examples:

Example

Transform 5324 (decimal) into decimal number (?!) using method of


continuous dividing – result 5324

5324 : 10 = 532 , remaining 4 100 last digit


532 : 10 = 53 , remaining 2 101
53 : 10 = 5 , remaining 3 102
5 : 10 = 0 , remaining 5 103 first digit

- end of procedure
Example

Transform 0,8125 (decimal) into decimal number (?!) using method of


continuous multiplying – result 0,8125

0,8125 * 10 = 8, 125 10-1 first digit after zero


0,125 * 10 = 1, 25 10-2
0,25 * 10 = 2, 5 10-3
0,5 * 10 = 5, 0 10-4 last digit

0,0 end of procedure

Decimal 2 Binary

Example

Transform 29 (decimal) into binary number - reading upwards, result


is111012

29 : 2 = 14 , remaining 1 20 last (smallest) digit


14 : 2 = 7 , remaining 0 21
7 : 2 = 3 , remaining 1 22
3 : 2 = 1 , remaining 1 23
1 : 2 = 0 , remaining 1 24 first digit

- end of procedure
Example

Transform 0,8125 (decimal) into binary number – reading downwards, result


is0,11012

0,8125 *2= 1, 625 2-1 first digit after zero


0,625 *2= 1, 25 2-2
0,25 *2= 0, 5 2-3
0,5 *2= 1, 0 2-4 last digit

0,0 end of procedure

Example

Transform 0,3 (decimal) into binary number – result is 0,01001 1001


1001… 2shortly rounded = 0,010012

0,3 * 2 = 0, 6 2-1 first digit after zero


0,6 * 2 = 1, 2 2-2
--------
0,2 * 2 = 0, 4 2-3
0,4 * 2 = 0, 8 2-4
0,8 * 2 = 1, 6 2-5
0,6 * 2 = 1, 2 2-6
--------

procedure never ends

Example – Quick Method

Transform 53(decimal) into binary number using quick method

53 25 + 24 + 22 + 20 =
- 32 -> 25 1*25 + 1*24 + 0*23 + 1*22 + 0*21 + 1*20 =
-------- 110101 2
21
- 16 -> 24
--------
5
- 4 -> 22
--------
1
- 1 -> 20
--------
0 -> end of procedure

Decimal 2 Hex
Example

Transform 2540,34 (decimal) into hex number-result ~ 9EC, 570A316

a) left from”,”

2540 : 16 = 158 , remaining 12 => C 160 last digit


1
158 : 16 = 9 , remaining 14 => E 16
9 : 16 = 0 , remaining 9 => 9 162 first digit

end of procedure => 9EC 16

b) right from “,”

0,34 * 16 = 5,44 5 => 5 16-1 first digit after zero


-2
0,44 * 16 = 7,04 7 => 7 16
0,04 * 16 = 0,64 0 => 0 16-3
0,64 * 16 = 10,24 10 => A 16-4
0,24 * 16 = 3,84 3 => 3 16-5


procedure could be continued => 0, 570A3… 16

Final result ~ 9EC , 570A316


Binary 2 Decimal

Example

Transform 110101 (binary) into decimal number

110101 2 = 1*25 + 1*24 + 0*23 + 1*22 + 0*21 + 1*20


= 1*25 + 1*24 + 1*22 + 1*20
= 1*32 + 1*16 + 1*4 + 1*1
= 53 10

Example

Transform -11,101 (binary) into decimal number

-11,101 2 = - (1*21 + 1*20 + 1*2-1 + 0*2-2 + 1*2-3)


= - (1*21 + 1*20 + 1*2-1 + 1*2-3)
= - (1*2 + 1*1 + 1*0,5 + 1*0,125)
= - 3 , 625

Hex 2 Decimal
Example

Transform 9EC,570A3 (hex) into decimal number

9EC, 570A3 16 = 9*162 + 14*161 + 12*160 + 5*16-1 + 7*16-2 + 0*16-3 +


10*16-4 + 3*16-5

= 2304 + 224 +12 + 0,3125 + 0,02734375 +


0,0001525878... + 0,00000286102...

= 2540 , 33999919891357421875

Quick Method of Transforming between Binary, Hex and Octal System

Binary Hex Binary Octal

0000 0 000 0
0001 1 001 1
0010 2 010 2
0011 3 011 3
0100 4 100 4
0101 5 101 5
0110 6 110 6
0111 7 111 7
1000 8
1001 9
1010 A
1011 B
1100 C
1101 D
1110 E
1111 F

Example

Transform -6F,A 16 into binary number

-6F,A 16 = - 0110 1111 , 1010 2 = - 1101111 , 101 2

Example

Transform 11,000011001 2 into hex number

11,000011001 2 = 11 , 0000 1100 1 2

= 0011 , 0000 1100 1000 2


= 3 , 0 C 8 16
= 3 , 0C8 16

Example

Transform 37,24 8 into binary number

37,24 8 = 011 111 , 010 100 2 = 11111 , 0101 2


Example

Transform 1111011,10011101 2 into octal number

1111011,10011101 2 = 1 111 011 , 100 111 01 2


= 001 111 011 , 100 111 010 2
= 1 7 3 , 4 7 2 16
= 173 , 472 16

math.h
Published Sunday, March 05, 2006 by Vurdlak | E-mail this post

#include <math.h>, syntax at the beginning of our code, means we automatically included
these (pre-defined) functions in our program:

int abs (int x); IxI

long labs (long x);

double fabs (double x);


double sin (double x);
double cos (double x);
double tan (double x);
double asin (double x);
double acos (double x);
double atan (double x);
double sinh (double x);
double cosh (double x);
double tanh (double x);
double exp (double x); ex

double log (double x); ln x

double log10 (double x); log x

double pow (double x,double y); xy

double sqrt(double x); sqare root of x

double fmod(double x, double y); x mod y

double ceil (double x);


double floor(double x);

stdlib.h
Published Sunday, March 05, 2006 by Vurdlak | E-mail this post

#include <stdlib.h>, syntax at the beginning of our code, means we automatically included
these (pre-defined) functions in our program:

void exit (int status);

void randomize (void); or void srand (unsigned int seed);

int rand (void);

string.h
Published Sunday, March 05, 2006 by Vurdlak | E-mail this post

#include <string.h>, syntax at the beginning of our code, means we automatically included
these (pre-defined) functions in our program:

char *strcpy(char *dest, const char *src);

char *strncpy(char *dest, const char *src, size_t maxlen);

char *strcat(char *dest, const char *src);


size_t strlen(const char *s);

char *strlwr(char *s);

char *strupr(char *s);

int strcmp(const char *s1, const char *s2);

int strcmpi(const char *s1, const char *s2);

int stricmp(const char *s1, const char *s2);

int strncmp(const char *s1, const char *s2, size_t maxlen);

int strncmpi(const char *s1, const char *s2, size_t maxlen);

int strnicmp(const char *s1, const char *s2, size_t maxlen);

char *strchr(const char *s, int c);

char *strstr(const char *string, const char *substring);

ctype.h
Published Sunday, March 05, 2006 by Vurdlak | E-mail this post

#include <ctype.h>, syntax at the beginning of our code, means we automatically included
these (pre-defined) functions in our program:

int toupper(int ch);

int tolower(int ch);

int isdigit(int c); figure (0-9)

int isalpha(int c); letter (A-Z or a-z)

int isalnum(int c); letter (A-Z or a-z) or figure (0-9)

int isprint(int c); character which can be printed (0x20-0x7E)

int iscntrl(int c); control char (0x7F or 0x00-0x1F)

int isspace(int c); empty space

int islower(int c); letter (a-z)

int isupper(int c); letter (A-Z)


alloc.h
Published Sunday, March 05, 2006 by Vurdlak | E-mail this post

#include <alloc.h>, syntax at the beginning of our code, means we automatically included
these (pre-defined) functions in our program:

void *malloc (size_t size); NULL error

void free (void *block);

void *realloc(void *block, size_t size); NULL error

You might also like