Vous êtes sur la page 1sur 38

Some Basics

Lexicon Rules that determine which symbols could be


used in the programming language
Syntax Rules that determine appropriate ways of
collating the symbols.
Semantics Recognize the meaning of every statement.
Instruction List (machine language) computers mother
tongue.
High level programming language - Portability
Translator HL to Machine Language
Compiler is a translator
Executable Translated/Compiled
Linker Link executable codes.
Chapter 1:
Puts
Puts(Its me, your first program!);
is in <stdio.h> header file.
Only strings;

return 0;
0 right
1 wrong

Syntax main
#include<stdio.h>
int main(void)
{
declarations;
instructions;
return 0;
}

#include<stdio.h> - pre processor directive.


Preprocessor is separate part of the compiler which pre-reads
the text of the programs and makes some changes to it, before
compilation.

Number systems
octal preceded by 0 & limits (0-7)
eg 0123
hexadecimal preceded by 0x & limits (0-9-a-f)

float %f
decimal - %d

Rules for variable & functions names


1. letter, digits and _

2. must begin with letter, _ is a letter


3. case sensitive
4. _ is also a variable name.
5. no spaces

Variable
int a;
%d
int a,b,c;
a = 1;
r = 1 + 2;
means equals r = 3 not 1
a variable cannot be declared type more than once.

Reserved Key Words

Comments
Each comment = one space
//

/* comments */

/**************
**************/
No nesting of comments allowed

Data Types
int integer type
%d
long
short
unsigned
literals of type long = 102901L or 102901l
float floating point type decimal fraction
%f
.4 can be used
4.0 makes 4 a floating point
short, unsigned not usable
long can be used
long float = double
accuracy us doubled compared to float
numerical anamoly if a very large flot and very small float are
added the smaller float is seem omitted in the result.

4 bytes 32 bits for int value => range


(-2147483648..2147483647) = (2^32)/2 thats 21474.. shit
and also total number of values in this range in 2^32+1
non negative range (0 (2^32-1))
(0 - 4294967296)
but ofcourse!
char
see char type in upcoming

cannot use long, and short


can use unsigned char
unsigned char (0 - 255)
char(-128 - 127)
Implementation depedent issues
A problem in software portability

3E8 3*10^8
3.4544E9
6.637E-34
Operators
* multiplication operator
/ division operator
+ addition operator

a%b remainder operator


13%5 = 3
none of the arguments can be a float

uniary operator 1 argument


binary operator 2 arguments
ternary operator 3 arguments

hirrerarchy of priorities
2+3*5 = 17

left binding and right binding

i++; used and modified; post incrementation


++i: modified and used; pre incrementation
i*=2;
i = i*2;
i +=2
i = i+2;
i%=2
i = i%2;
i/=2
i = i/2;

if operations happen link in


int I;
I = (some floating point shit)
Floating results are turnicated into int results at every step.
Char type
In C language all strings are treated as arrays
char C;
characters are stored as numbers
ASCII American standard code for information interchange
EBIDIC dont know what the fuck this is but also used by
some computers like IBM main frames.

ASCII provides for 256 characters; were interested in first 128


only.

Characte
r
(NUL)
(SOH)
(STX)
(ETX)
(EOT)
(ENQ)
(ACK)
(BEL)
(BS)
(HT)
(LF)
(VT)
(FF)
(CR)
(SO)
(SI)
(DLE)
(DC1)
(DC2)
(DC3)
(DC4)
(NAK)
(SYN)
(ETB)
(CAN)
(EM)
(SUB)
(ESC)
(FS)
(GS)
(RS)

Dec
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30

Hex
0
1
2
3
4
5
6
7
8
9
0A
0B
0C
0D
0E
0F
10
11
12
13
14
15
16
17
18
19
1A
1B
1C
1D
1E

Characte
r
(space)
!
"
#
$
%
&
'
(
)
*
+
,
.
/
0
1
2
3
4
5
6
7
8
9
:
;
<
=
>

Dec
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62

Hex
20
21
22
23
24
25
26
27
28
29
2A
2B
2C
2D
2E
2F
30
31
32
33
34
35
36
37
38
39
3A
3B
3C
3D
3E

(US)

Characte
r
(NUL)
(SOH)
(STX)
(ETX)
(EOT)
(ENQ)
(ACK)
(BEL)
(BS)
(HT)
(LF)
(VT)
(FF)
(CR)
(SO)
(SI)
(DLE)
(DC1)
(DC2)
(DC3)
(DC4)
(NAK)
(SYN)
(ETB)
(CAN)
(EM)
(SUB)
(ESC)
(FS)
(GS)

31

1F

Dec

Hex

64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93

0
1
2
3
4
5
6
7
8
9
0A
0B
0C
0D
0E
0F
10
11
12
13
14
15
16
17
18
19
1A
1B
1C
1D

Characte
r
(space)
!
"
#
$
%
&
'
(
)
*
+
,
.
/
0
1
2
3
4
5
6
7
8
9
:
;
<
=

63

3F

Dec

Hex

96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125

20
21
22
23
24
25
26
27
28
29
2A
2B
2C
2D
2E
2F
30
31
32
33
34
35
36
37
38
39
3A
3B
3C
3D

(RS)
(US)

94
95

1E
1F

A 65
a 96
A-a = 32
And blank space is also 32 in ASCII
char c;
c = A;
this is also equivalent to
c = 65;
c = ?;
how to declare a char
like this
char c = \
\ - escape character
also
char c = \\

chars can be assigned to int;


operations can be done in char values.

>
?

126
127

3E
3F

char a,b,c;
c = a+b;

Literal
A, 32, a, 100
A symbol that identifies its value.
Expression
Made up of variable and literals and operators.
32 + i

Escape character
\n new line or line feed
\r return to the beginning of the line
\a alarm
\0 null
\octal like
\47 will be treated as ASCII value.
So, \47 = ASCII symbol equivalent of octal 47 (or 38 decimal
sumbol equivalent in ASCII) that is

So,
char c = \47 =>
char c = 38 =>

char c = \

same goes for hexadecimal


c = \47 = 38 = \x27
==
!=
> strict
>= non strict
has very low priority
when answer assigned to an integer type we have
1 true
0 false

Conditional Instructions
if statement the value inside should be 0 or non zero. The
result hence follows.

if()
{;}

if()
{;}
else

{;}

if()
{
if()
{;}
else
{;}
}
else
{
if()
{;}
else
{;}
}

if()
{;}
elseif()
{;}
elseif()
{;}
elseif();
{;}
else
{;}

Switch case
switch(i){
case 1: inst; break;
case 2: inst; break;
case 3: inst;
}

switch(i){
case 1: inst; break;
case 2: inst; break;
case 3: inst; break;
default: inst;
}

Input and output


Output
printf() print formatted.
int a;
Printf(fucked! = %d, a)
% - specifier
%d decimal
%i integer

%x value of type int represented as fixed point hexadecimal


%0 fixed point octal
%c char
%f float
%% - display %
mistakes
if specifiers > arguments random output for orphan specifier
if arguments > than specifiers the extra arguments will not be
displayed.
If specifier = float and argument is int. some random shit will
be displayed. Viceversa is more so random shit.
If specifier is int and argument is char then the ASCII value
will be put.

Output

int sex;
scanf() scan formatted
scanf(%d, &sex)

Square Root
#include <math.h>
sqrtf();

Conversions/ Metamorphosis
Implicit - @runtime; not seen in code; have rules.
Rules
1. Integer promotion type char or short -> int
2. if there is float in the expression, other values will be
converted into float
3. if there is double in the expression, others will be
converted into double.
4. if there is long int, other data will be converted into long
int as well.
Explicit Typecast operator. High priority is used.
(type)value;
float x;
double y;
y = (double)x;

Loops
while()
{statement;}

while(1) infinite loop

do
{;}
while();

for(i=0; i<100; i++)


{;}

for(;;) infinite loop.


{;}
if you leave anything in if loop, then its treated that there is 1
there, and it becomes infinite loop.

break;
- Will exit the loop
continue;
- Will restart the loop
Its possible to do the program without these. Some fucker
proved it.

Computer Logic

&&
- lower priority than ==
||
- lower priority than ==
!arg
very high priority

demorgans law
!(p&&q) == !p || !q
!(p||q) == !p && !q

Bitwise Operators
& - conjunction
| - disjunction
~ - negation
^ - exclusive
so the argument ints will will converted into binary; operated;
converted back to decimal.
Also
x = x&y
x &= y

can use int, short, long as arguments only.


Set = 1
Reset = 0

Reseting your bit

Identifying if bit is set or reset

Set your bit

Negate your bit

Here we have used XOR


X^1 = !X
X^0 = X

Bit shifting
Logical if all the bits of the variable are shifted. When
applied to unsigned integers.
Arithemetic The shift omits sign bit. (in 2s compliment
nitation, the highest bit is sign bit. 1 negative; 0-positive)

Value << bits left shift. => multiplication by 2


Value >> bits right shift => division by 2

Arrays
int numbers[5];
indexed from 0
numbers[0] = 111; - putting in a number in 1st position.
i = numbers[2]; - pulling out the 3rd number in the array
int numbers[5] = {3,2,5,2,3};
if you provide lesser values than remaining will be set to zero
if you provide more values than specified compilation error

int numbers[] = {3,2,5,2,3};


float numbers[] = {3.32 ,2.43 ,5.3223, 3.232, 3.33};
char bullshit[20] initiation is different see it in strings.

Reversing the order of elements in an array

tip count up till the middle element only.

Sorting an array
Bubble sort very inefficient; certainly not used in large
arrays;
So, we take pairs of consequitive (1,2) (2,3) (3,4) (n-1,n) and
swap conditionally 1st pass
..swap.till (n-1) second pass
..
..
..
..swap.till (n-1) passes

for 5 elements we need 4 swaps means in for loop we go (0-3)

better algo .. when you can avoid unnecessary swaps by


checking for goodness is status quo using do while.

Pointers
Variable
Value = is what variable stores.
Address = Information about where this variable is placed.
Pointer = store the address of a variable.

int *p
sets up a variable
p - its not an int
presence of * => p = pointer
has information address of some data of type int

data type of p = is of data type pointer to int


is of data type int*

*p = 0; (or) *p = NULL; - null pointer


*p = 8273838; not allowed.

Assignment
We just store address of a variable into the pointer.
i = variable
&i = address of the variable
p = &i;

- assignment to a pointer

example

int ivar, *ptr;


ivar = 2;
ptr = &ivar
dereferencing
by placing * before ptr i.e., *ptr
I get the value stored at the address stored
by the ptr variable. i.e., I get what is stored at address of ivar;
so I get ivar? FACK??!!!!

ans = 3;
so, *ptr gives what is stored at the address value in ptr variable.
dereferencing. get a value pointed to pointer.
ptr = address; referencing
*ptr = value at address; dereferencing
dereferencing NULL pointer is forbidden and causes runtime
error.

*ptr = 4 -> changes value pointed to by the pointer.


sizeof(arg)

only operaor in in C which accepts argument as data type name


highest possible priority
int c
int i = typeof(int)
int j = type of c
need to use parenthesis when using data type as argument.

Char tab[10];
i = sizeof tab;
i = 10
i size of tab[1];
i=1
int I;
sizeof I = 4 (32 bits)
each char occupies one byte = 8 bits (255)

Name of an array without indices is a pointer pointing to the


first element of the array.
int *ptr, array[3];
ptr = array[0];
(*ptr == array) is true

so the array name is actually a pointer which when


dereferenced will give us value of 1st element in the array.
A direct dereferencing of the array name also works.

Arithemetic of pointers
Possibilities
1. Adding if integer values to the pointer
ptr = ptr + 9;
adds a value 9* sizeof(*ptr) to the address value in ptr.
Hence changes the value of address in ptr to the address of next
chunk of data.
The new address is n bytes more than the previous address.
Where, n = the size of data in old address.
2. Subtracting an integer value from a pointer.
Same shit happens
3. Subtracting a pointer from a pointer.
Both pointers need to point to data of same data type
The addresses stored are subtracted. The result is divided by
typeof(data type). So, it tells how many such variables can fit
between the two variables.

4. Comparing two pointers.


Yah

Strings
#include<string.h>
char protagonist[] = snape; 5 letters
Similar to
char[6] = snape;
How is this handled?
1. compiler counts the number of characters n
2. reserves space for n+1 chars
3. copies entire string and appends \o in the end
4. treats the string name as pointer to the reserved memory

Im trying to size the value of the data pointed to by snape


string. Sizeof(*snape)

But, *protagonist = *snape => compiler says fuck off.


Now,
char *hero = Dumbledore;
handling
1. reserve space for 10+1 chars;
2. store that string and append \0
3. create variable hero.
4. Assign address of the string to variable hero.
So, if you dereference here, you get the first letter of D.
Printing a string
1. int puts(char *s);
if it works o/p is non negative number; if it doesnt then
we get -1; Puts automatically adds new line.
2. puts(protagonist);
3. puts(hero);
4. puts(boomer);
5. int printf(char *format, );
result of printf is the number of characters it sends out
successfully.
6. printf(%s and %s, protagonist, hero);

String Length
strlen(ptr)
strlen(someshit)

String Copy
strcpy(string, ptr)
strncpy(string, ptr, 3)

String Append
strcat(string, ptr)

Modifying Strings
char word[] = dump;
word[1] = a;
printf(%s,word);
ans = damp
word[232222] = a; - memory protection error;
Indexing Operators
int *t;
now if we use indexing operator on t.
t[i];

t[i] is nothing but


*(t+i)
t[0] = *t
t[1] = *(t+1)

word[0] = *(word)
word[i] = *(word+i)

*(word +1) gives the value of word[i]


*word +1 adds 1 to word[0]

int *t
t[i] = i[t]
how?
t[i] = *(t+i) = *(i+t) = i[t]
word[1] = 1[word] = a

it works? What the actual fuck?!!!

char string[] = some shit;


int *p;
c = *p++; string[1]
c = *(p)++; string[0]++

Multidimensional arrays
float temp[34][54] = {{},{}} = {,,,,,,,}
rows colums

Malloc

Dynamic Array Arrays using pointers and malloc.


One more example below; Summing an array. The below form
of usage is called dynamic array. Possible by using []
indexing operator and malloc.
int *p

p = (int*)malloc(5*sizeof(int))

Vous aimerez peut-être aussi