Timings

N[Pi,10^2]

Timing[N[Pi,10^3]]

Timing[N[Pi,10^4];]
Timing[N[Pi,10^5];]

Timing[p=N[Pi,10^6];]

N[E,10^7];//Timing

Blocks
If[], Which[], Switch[], With[], Module[], Block[] ...
Look up the constructs in the Mathematica guide!

Array[v,{4}]

With[{
x=0, 
y=Apply[Plus,Array[v,{4}]]
},

With[{
x=1
},
Print["x=",x,"   y=",y];
];
Print["x=",x,"   y=",y];
]

Clear[x,y]

With[{
x=4,
y=x+5},

{x,y}
]

With[{a,b},
Pi]

Probably that was not what you're looking for. 
Module[]

a=5;b=2;
Module[{a,b,c,d},
Pi+a+b]

Clear[x,y]

Module[{
x=4,
y=x+5},

{x,y}
]

Block[]

Block[{
x=4,
y=x+5},

{x,y}
]

Block[{
y=x+5,
x=4},

{y,x}
]

Example: Fibonacci

What's the most efficient way to compute the n-th number of the Fibonacci sequence?

1) Recursive   - FibR

fibR[0]=0;
fibR[1]=1;
fibR[n_Integer?Positive]:=fibR[n-1]+fibR[n-2]

fibR[30]//Timing

n=16;
calls=Table[0,{n+1}]

fibR[0]:=(calls[[1]]++;0);
fibR[1]:=(calls[[2]]++;1);
fibR[n_Integer?Positive]:=(calls[[n+1]]++;fibR[n-1]+fibR[n-2])

fibR[n]

calls

2) Dynamic Programming  - FibD

Clear[fibD]

$RecursionLimit=100000;
fibD[0]=0;
fibD[1]=1;
fibD[n_]:=fibD[n]=fibD[n-1]+fibD[n-2]

?fibD

fibD[10]

?fibD

fibD[11]

?fibD

fibD[100000]

2+3

?fibD

MemoryInUse[]

?fibR

?fibD

fibD[30]

?fibD

$RecursionLimit=100000;
fibD[0]=0;
fibD[1]=1;
fibD[n_]:=fibD[n]=fibD[n-1]+fibD[n-2]

Timing[fibD[30]]

fibD[1000]//Timing

fibD[1000]//Timing

3) Imperative: While, For, Do  - FibI, FibI2

?For

fibI[n_]:=
(
For[
i=1;t0=0;t1=1,
i<n,
i++,
{t0,t1}={t1,t0+t1}
];
t1
)

fibI[1000]

?For

fibI2[n_]:=
(
For[
i=1;t0=0;t1=1,
i<n,
i++,
aux=t0;t0=t1;t1=aux+t1
];
t1)

fibI2[1000]

4) Symbolic  - FibS, FibS2

Solve[{x+y==4,x-y==-1},{x,y}]

RSolve[{
g[n]==g[n-1]+g[n-2],
g[1]==1,
g[0]==0
},
g[n],n]

fibS2[n_]:=Fibonacci[n]

Clear[fibS]

fibW[n_]:=-((((((1/2)-((Sqrt[5])/2)))^n)-((((1/2)+((Sqrt[5])/2)))^n))/(Sqrt[5]))

fibW[40]

(a+b)^4//Expand

fibW[40]//Expand

fibS[n_]:=Expand[-((((((1/2)-((Sqrt[5])/2)))^n)-((((1/2)+((Sqrt[5])/2)))^n))/(Sqrt[5]))]

fibS[150]
fibS2[150]

fibS[1000]//Timing

5) Numeric  - FibN

Clear[fibN]

fibW[n_]:=N[-((((((1/2)-((Sqrt[5])/2)))^n)-((((1/2)+((Sqrt[5])/2)))^n))/(Sqrt[5]))]

fibS[2500]//Timing

fibW[2500]//Timing

fibN[n_]:=N[-((((((1/2)-((Sqrt[5])/2)))^n)-((((1/2)+((Sqrt[5])/2)))^n))/(Sqrt[5])),Round[n/2]]

fibN[1000]

fibS[1000]

fibN[1000]-fibS[1000]

fibN2[n_]:=-(((((.5-((Sqrt[5.])/2)))^n)-(((.5+((Sqrt[5.])/2)))^n))/(Sqrt[5.]))

fibN2[1000]

fibN2[1000]-fibS[1000]

fibN2[1000]//Timing

6) Functional  - FibF

next[{x_,y_}]:={y,x+y}

?Nest

Nest[f,x0,5]

fibF[n_]:=
Nest[next,{0,1},n-1][[2]]

fibF[1000]//Timing

7) Matrix Form  - FibM

M1={{0,1},
     {1,1}};
M2={{a,b},
     {b,a+b}};
MatrixForm /@
{M1,
M1.M1,
M1.M1.M1,
M1.M2,
M1.M1.M1.M1}

Table[MatrixForm[MatrixPower[{{0,1},{1,1}},i]],{i,7}]

fibM[n_]:=
MatrixPower[{{0,1},{1,1}},n-1][[2,2]]

fibM[1000]

Tests - correctness

$RecursionLimit= 10000

Map[
#[100]&,{fibD,fibI,fibI2,fibS,fibS2,fibN,fibF,fibM}
]

With[{
res=Map[
#[1000]&,
{fibI,fibI2,fibS,fibS2,fibN,fibF,fibM}
]},
Norm[res-res[[1]]]
]

Clear[fibD];
fibD[0]=0;fibD[1]=1;
fibD[n_]:=fibD[n]=fibD[n-1]+fibD[n-2];

Map[
Flatten@{#,Timing[#[100];]}&,
{fibD,fibI,fibI2,fibS,fibN,fibF,fibM,fibS2}
]//MatrixForm

Tests - speed

definitions

fibI[n_]:=
(
For[
i=1;t0=0;t1=1,
i<n,i++,
{t0,t1}={t1,t0+t1}
];
t1
)

fibI2[n_]:=
(
For[
i=1;t0=0;t1=1,
i<n,
i++,
aux=t0;t0=t1;t1=aux+t1
];
t1)

fibS[n_]:=Expand[-((((((1/2)-((Sqrt[5])/2)))^n)-((((1/2)+((Sqrt[5])/2)))^n))/(Sqrt[5]))]

fibS2[n_]:=Fibonacci[n]

fibN[n_]:=N[-((((((1/2)-((Sqrt[5])/2)))^n)-((((1/2)+((Sqrt[5])/2)))^n))/(Sqrt[5])),Round[n/2]]

next[{x_,y_}]:={y,x+y}

fibF[n_]:=
Nest[next,{0,1},n-1][[2]]

fibM[n_]:=
MatrixPower[{{0,1},{1,1}},n-1][[2,2]]

Map[
Flatten@{#,Timing[#[10000];]}&,{fibI,fibI2,fibS,fibN,fibF,fibM,fibS2}
]//MatrixForm

Map[
Flatten@{#,Timing[#[500000];]}&,{fibI,fibI2,fibN,fibF,fibM,fibS2}
]//MatrixForm

Map[
Flatten@{#,Timing[#[1000000];]}&,{
fibN,fibM,fibS2}
]//MatrixForm

Map[
Flatten@{#,Timing[#[100000000];]}&,{fibM,fibS2}
]//MatrixForm

Patterns - RECAP

t[ _[_, a_]]:= Pi

t[ f_[x_, y_]]:= {f,x,y}

t[g[a,b]]

t[Sin[x,y]]

t[Sin[x+y]]

t[Sin[3+Pi]]

Sin[3+Pi]

Optional arguments

f[a_,b_,c_,mode_:"Lower"]:=
Switch[mode,
"Lower",{{a,0},{b,c}},
"Upper",{{a,b},{0,c}},
mode,Print["I don't understand you"];Abort[]
]

f[Pi,E,3]//MatrixForm

f[Pi,E,3,"Lower"]//MatrixForm

f[Pi,E,3,"lower"]//MatrixForm

isLowerQ[M_]:=M[[1,2]]==0

isLowerQ[{{_,0},{_,_}}]:=True

isLowerQ[_]:=False

isLowerQ[f[1,2,3]]

isLowerQ[f[1,2,3,"Upper"]]

Clear[f]

f[a_^b_]:={a,b}

{
f[1^2],
f[2^1],
f[Pi^(t+y)],
f[(t+y)]
}

ff[a_^(b_:1)]:={a,b}

{
ff[1^2],
ff[2^1],
ff[Pi^(t+y)],
ff[(t+y)]
}

HoldForm[1^2]

Clear[f]

f[{{a_,0,0},
{b_,c_,0},
{d_,e_,f_}}]:={d,e,f}

f[{{1,2,3},{4,5,6},{7,8,9}}]

f[{{1,0,0},{4,5,0},{7,8,9}}]

g[{{_,0,0},
{_,_,0},
r:{_,_,_}}]:=r

g[{{1,0,0},{4,5,0},{7,8,9}}]

Recap

f[x_]:= (* general function definition *)

f[x_List]:= (* restricting the type of the arguments *)

f[x_,y_]:= (* multiple arguments *)

f[x_,"a"]:= (* fixing one of the arguments *)

f[x_/?NumberQ[x]]:= 
(* test on argument x *)

f[x_,y_,z_/;condition[z]]:= (* condition on argument z *)

f[x_,y_,z_]/;condition[x,y,z]:=(* condition on arguments *)

f[a_,b__,l___]:=
(* matching one element, a non-empty sequence of elements, any sequence *)

f[a_+b_]:=(* specifying the structure of the argument *)

f[{{a_,b_},___}]:=(* again, specifying the structure of the argument *)

f[m:{_^b_}]:=Power[m,-b](* assigning names to parts of a pattern *)

f[a_,b_:Pi]:=Sin[a+b] (* default arguments *)

#&
#1+#2&
##&    (* triple underscore *) 
Function[{t},t^2]
Function[{t,v},t^2+v]

g/@{arg0,arg1,arg2}

g@@{arg0,arg1,arg2}

Apply[g,{arg0,arg1,arg2}]

g@{arg0,arg1,arg2}

{arg0,arg1,arg2}//g

a~g~b