algoritmo

Propaganda
INE5403
F UNDAMENTOS DE
M ATEMÁTICA D ISCRETA
PARA A C OMPUTAÇÃO
P ROF. M AURO R OISENBERG
UFSC - CTC - INE
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 1/2
2 - N ÚMEROS I NTEIROS
2.1) Divisão nos Inteiros
2.2) Números Primos e MDCs
2.3) Inteiros e Algoritmos
2.4) Aplicações de Teoria dos Números
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 2/2
I NTRODUÇÃO
Existem várias classes de problemas que aparecem na Matemática
Discreta:
dada uma seqüência de inteiros, ache o maior;
dado um conjunto liste todos os seus subconjuntos;
dado um conjunto de inteiros, coloque-os em ordem crescente;
dada uma rede de comunicação, ache o menor caminho entre
dois vértices.
Quando apresentado a estes problemas, a primeira coisa a fazer é
construir um modelo que traduza o problema em um contexto
matemático.
Achar o modelo matemático adequado é apenas parte da solução.
Para completar a solução é necessário um método que solucionará o
problema geral utilizando o modelo.
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 3/2
I NTRODUÇÃO
O método consiste em procedimento com uma seqüência de passos
que levam até a resposta desejada. Tal seqüência de passos é
chamada de um algoritmo.
Definição: Um algoritmo é um conjunto finito de instruções precisas
para realizar um cálculo ou solucionar um problema.
O termo algoritmo muitas vezes é utilizado para designar
procedimentos para realizar operações aritméticas usando a
representação decimal dos inteiros.
Estes algoritmos, adaptados para serem utilizados com a
representação binária, são a base para a aritmética
computacional.
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 4/2
R EPRESENTAÇÃO
DOS I NTEIROS
No nosso dia-a-dia utilizamos na notação decimal para expressar
números inteiros. Por exemplo, 965 é utilizado para denotar
9.102 + 6.10 + 5.
Podemos utilizar outras bases, além da decimal.
Computadores normalmente utilizam notação binária (base 2)
para realizar operações aritméticas.
De fato, podemos utilizar qualquer inteiro positivo maior que 1
como base quando expressamos inteiros, como mostrado pelo
seguinte teorema:
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 5/2
E XPANSÃO
DE
n NA
BASE
b
Teorema 1: Seja b um inteiro positivo maior que 1. Então se n é um
inteiro positivo, ele pode ser expresso de maneira única na forma
n = ak bk + ak−1 bk−1 + · · · + a1 b1 + a0
onde k é um inteiro não negativo, a0 , a1 , · · · , ak são inteiros não
negativos menores que b, e ak 6= 0.
A expansão de n na base b (nome do Teorema 1) é denotada por
(ak ak−1 · · · a1 a0 )b .
Por exemplo, (245)8 representa 2.82 + 4.8 + 5 = 165.
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 6/2
E XPANSÕES B INÁRIAS
Na notação binária, cada dígito pode ser 0 ou 1. Em outras palavras,
a expansão binária de um inteiro é uma “cadeia” (string) de bits.
Expansões binárias são utilizadas por computadores para
representar e realizar a aritmética com inteiros.
Exemplo 1: Qual a expansão decimal de um inteiro que possui
(101011111)2 como sua expansão binária?
(101011111)2 =
1.28 + 0.27 + 1.26 + 0.25 + 1.24 + 1.23 + 1.22 + 1.21 + 1.20 = 351
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 7/2
E XPANSÕES H EXADECIMAIS
16 dígitos diferentes são necessários para esta expansão. Os dígitos
hexadecimais utilizados são: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E e F ,
onde as letras A até F representam os dígitos correspondentes aos
números 10 a 15 (na notação decimal).
Exemplo 2: Qual a expansão decimal de um inteiro que possui
(2AE0B)16 como sua expansão hexadecimal?
(2AE0B)16 = 2.164 + 10.163 + 14.162 + 0.161 + 11.160 = (175627)10
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 8/2
C ONVERSÃO
DE
BASE
Como construir a expansão de um inteiro n na base b.
Primeiro, divida n por b para obter um quociente e um resto, ou
seja:
n = bq0 + a0 , com 0 ≤ a0 < b.
O resto, a0 , é o dígito mais a direita na expansão de n na base b.
A seguir divida q0 por b para obter:
q0 = bq1 + a1 , com 0 ≤ a1 < b.
a1 é o segundo dígito da direita na expansão de n na base b.
Continue este processo, dividindo sucessivamente os quocientes
por b. Este processo termina quando se obtém um quociente
igual a zero.
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 9/2
C ONVERSÃO
DE
BASE
Exemplo 3: Ache a expansão octal (base 8) de (12345)10 .
Primeiro, divida 12345 por 8 para obter
12345 = 8.1543 + 1
Sucessivamente divida os quocientes por 8
1543 = 8.192 + 7
192 = 8.24 + 0
24 = 8.3 + 0
3 = 8.0 + 3
Assim a expansão de 12345 na base 8 é dada pelos restos
obtidos:
(12345)10 = (30071)8 .
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 10/2
A LGORITMO
PARA
C ONVERSÃO
DE
BASE
O pseudo-código a seguir acha a expansão (ak−1 · · · a1 a0 )b de um
inteiro n na base b.
Algoritmo 1: Construindo Expansões Base b
procedure base b expansion(n:positive integer)
q := n
k := 0
while q 6= 0
begin
ak := q mod b
q := bq/bc
k := k + 1
end {the base b expansion of n is (ak−1 · · · a1 a0 )b }
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 11/2
A LGORITMOS
PARA
O PERAÇÕES
COM I NTEIROS
Os algoritmos para realizar operações com inteiros usando suas
representações em expansões binárias são extremamente
importantes em aritmética computacional.
Descreveremos algoritmos para adição e multiplicação de dois
inteiros expressos como expansões binárias.
Analisaremos a complexidade computacional destes algoritmos em
termos do número de operações de bits necessárias para sua
execução.
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 12/2
A LGORITMO
PARA
S OMA
DE I NTEIROS
Sejam dois números a e b cujas expansões binárias são:
a = (an−1 an−2 · · · a1 a0 )2 , b = (bn−1 bn−2 · · · b1 b0 )2 ,
de tal forma que a e b possuem n bits (bits 0 podem ser colocados no início de uma
das expansões se necessário).
Para somar a e b, primeiramente some seus dígitos mais a direita:
a0 + b0 = c0 .2 + s0 ,
onde s0 é o bit mais a direita na expansão binária de a + b e c0 é o "vai um" (carry ),
que pode ser 0 ou 1.
A seguir some o próximo par de bits e o carry,
a1 + b1 + c0 = c1 .2 + s1 ,
onde s1 é o próximo bit na expansão binária de a + b, e c1 é o carry.
Continue este processo, somando os bits correspondentes nas duas expansões
binárias e o carry.
Este processo produz a expansão binária da soma de
a + b = (sn sn−1 sn−2 · · · s1 s0 )2 .
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 13/2
A LGORITMO
PARA
S OMA
DE I NTEIROS
Exemplo 4: Some a = (1110)2 e b = (1011)2 .
a0 + b0 = 0 + 1 = 0.2 + 1.
De forma que c0 = 0 e s0 = 1. Continuando o algoritmo:
a1 + b1 + c0 = 1 + 1 + 0 = 1.2 + 0.
De forma que c1 = 1 e s1 = 0. Continuando o algoritmo:
a2 + b2 + c1 = 1 + 0 + 1 = 1.2 + 0.
De forma que c2 = 1 e s2 = 0. Continuando o algoritmo:
a3 + b3 + c2 = 1 + 1 + 1 = 1.2 + 1.
De forma que c3 = 1 e s3 = 1. O que significa que s4 = c3 = 1.
Assim, s = a + b = (11001)2 .
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 14/2
A LGORITMO
PARA
S OMA
DE I NTEIROS
O pseudo-código a seguir acha a expansão binária (sn sn−1 · · · s1 s0 )2
da soma da expansão binária de dois inteiros a e b.
Algoritmo 2: Soma de Inteiros
procedure add(a,b:positive integer)
{the binary expansions of a and b are (an−1 an−2 · · · a1 a0 )2
and (bn−1 bn−2 · · · b1 b0 )2 respectively
c := 0
for j = 0 to n − 1
begin
d := b(aj + bj + c)/2c
sj := aj + bj + c − 2d
c := d
end
sn := c
{the binary expansion of the sum is (sn sn−1 · · · s0 )2 }
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 15/2
A NÁLISE
DO
A LGORITMO
Quantas adições de bits são necessárias no Algoritmo 2 para somar
dois inteiros com n bits (ou menos) na sua representação binária?
Dois inteiros são somados através da adição sucessiva de pares
de bits, e de um carry, quando ele ocorre.
Assim, o número total de adições de bits realizadas é menor ou
no máximo igual a três vezes o número de bits da expressão.
Podemos então dizer que o número de adições de bits realizadas
pelo Algoritmo 2 para somar dois inteiros de n−bits é
proporcional a n (O(n)).
Isto significa que, se somar dois inteiros de n bits leva um tempo
t, então a soma de dois inteiros de 2n bits leva um tempo 2t.
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 16/2
A LGORITMO
PARA
M ULTIPLICAÇÃO
DE I NTEIRO
Consideremos agora a multiplicação de dois inteiros a e b de n bits.
Usando a propriedade distributiva, vemos que:
ab = a(b0 20 + b1 21 + · · · + bn−1 2n−1 ) =
a(b0 20 ) + a(b1 21 ) + · · · + a(bn−1 2n−1 ).
Note que: abj = a se bj = 1 e abj = 0 se bj = 0
Além disso, cada vez que multiplicamos um termo por 2, “rotamos” a
sua expansão binária um bit para a esquerda e colocamos um 0 na
posição mais a direita da expansão binária.
Obtemos então (abj )2j “rotando” a expansão binária de (abj ) j
vezes para a esquerda, acrescentando j 00 s na direita da expansão.
Finalmente, obtemos ab somando os n inteiros
abj 2j , j = 0, 1, 2, · · · , n − 1
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 17/2
A LGORITMO
PARA
M ULTIPLICAÇÃO
DE I NTEIRO
O pseudo-código a seguir acha a expansão binária (sn sn−1 · · · s1 s0 )2
da multiplicação da expansão binária de dois inteiros a e b.
Algoritmo 3: Multiplicação de Inteiros
procedure multiply(a,b:positive integer)
{the binary expansions of a and b are (an−1 an−2 · · · a1 a0 )2 and (bn−1 bn−2 · · · b1 b0 )2
c := 0
for j = 0 to n − 1
begin
if bj = 1 then cj := a “rotado” j vezes
else cj := 0
end
{ c0 , c1 , · · · , cn−1 são os produtos parciais
p := 0
for j = 0 to n − 1
p := add(p, cj )
{p é o valor de ab }
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 18/2
A LGORITMO
PARA
M ULTIPLICAÇÃO
DE I NTEIRO
Exemplo 5: Multiplique a = (110)2 e b = (101)2 .
ab0 .20 = (110)2 .1.20 = (110)2 .
ab1 .21 = (110)2 .0.21 = (0000)2 .
e
ab2 .22 = (110)2 .1.22 = (11000)2 .
Basta agora somar (00110)2 + (00000)2 + (11000)2 , usando o
algoritmo da soma:
ab = (11110)2 .
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 19/2
A NÁLISE
DO
A LGORITMO
Quantas adições e “rotações” de bits são necessárias no Algoritmo 3
para multiplicar dois inteiros?
Como o Algoritmo 3 processa o produto de a e b somando os produtos parciais
c0 , c1 , c2 , · · · , cn−1 . E como para obter cada cj são necessárias j “rotações”,
então são necessárias no máximo:
0 + 1 + 2 + · · · + n − 1 “rotações”.
Assim, o número de “rotações” é proporcional (ou da mesma ordem de grandeza)
que n2 (O(n2 )).
Para somar os produtos parciais cj requerem a soma de um inteiro de n-bits, um
inteiro de n + 1-bits , · · · , e um inteiro de (2n)-bits,
Sabemos que cada uma destas operações requer um número proporcional a n
de operações de bits,
Conseqüentemente, o número de operações de bits necessárias para multiplicar
dois números é da ordem de grandeza de n2 (O(n2 )).
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 20/2
A LGORITMO
PARA
D IVISÃO
DE I NTEIROS
O pseudo-código a seguir calcula o quociente e o resto da divisão de
um inteiro a por um inteiro positivo d.
Algoritmo 4: Divisão de Inteiros (div e mod)
procedure division(a: integer, d:positive integer)
q := 0
r := |a|
while r ≥ d
begin
r := r − d
q := q + 1
end
if a < 0 and r > 0 then
begin
r := d − r
q := −(q + 1)
end
{ q = a div d é o quociente, r = a mod d é o resto
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 21/2
E XPONENCIAÇÃO M ODULAR
Em criptografia, é importante muitas vezes calcular de forma
eficiente bn mod m, onde b, n e m são números inteiros grandes.
Geralmente é impraticável calcular bn e então achar o seu resto
quando dividido por m, pois bn será um número muito grande.
Em vez disso, podemos usar um algoritmo que utiliza a expansão
binária do expoente n = (ak−1 · · · a1 a0 )2 .
O algoritmo acha sucessivamente b mod m, b2 mod m, b4 mod m,
2k−1
· · ·, b
mod m e se vale da seguinte propriedade:
c = (a.b)( mod m)
c = (a( mod m)).(b( mod m))( mod m)
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 22/2
A LGORITMO
PARA
E XPONENCIAÇÃO M ODULAR
Algoritmo 5: Exponenciação Modular
procedure modular exponentiation(b: integer, n = (ak−1 ak−2 · · · a1 a0 )2 ,
m:positive integer)
x := 1
power := b mod m
for i := 0 to k − 1
begin
if ai = 1 then x := (x.power) mod m
power := (power.power) mod m
end
{ x vale bn mod m }
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 23/2
A LGORITMO
PARA
E XPONENCIAÇÃO M ODULAR
Exemplo 6: Use o Algoritmo 5 para calcular 26 44 mod 645.
Inicialmente fazemos x = 1 e power = 2 mod 645 = 2.
A expansão binária de 644 = (1010000100)2 .
2j
O algoritmo calcula 2 mod 645 para j = 1, 2, · · · , 9
sucessivamente elevando ao quadrado e reduzindo modulo 645.
Se aj = 1 (onde aj é o bit na j−ésima posição da expansão
2j
binária de 644), ele multiplica o valor atual de x por 2 mod 645
e reduz o resultado módulo 645.
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 24/2
A LGORITMO
PARA
E XPONENCIAÇÃO M ODULAR
Exemplo 6
i = 0 : Como a0 = 0, temos x = 1 e power = 22 = 4 mod 645 = 4;
i = 1 : Como a1 = 0, temos x = 1 e power = 42 = 16 mod 645 = 16;
i = 2 : Como a2 = 1, temos x = (1.16) mod 645 = 16 e
power = 162 = 256 mod 645 = 256;
i = 3 : Como a3 = 0, temos x = 16 e power = 2562 = 65536 mod 645 = 391;
i = 4 : Como a4 = 0, temos x = 16 e power = 3912 = 152881 mod 645 = 16;
i = 5 : Como a5 = 0, temos x = 16 e power = 162 = 256 mod 645 = 256;
i = 6 : Como a6 = 0, temos x = 16 e power = 2562 = 65536 mod 645 = 391;
i = 7 : Como a7 = 1, temos x = (16.391) mod 645 = 451 e
power = 3912 = 152881 mod 645 = 16;
i = 8 : Como a8 = 0, temos x = 451 e power = 162 = 256 mod 645 = 256;
i = 9 : Como a9 = 1, temos x = (451.256) mod 645 = 1.
Prof. Mauro Roisenberg - UFSC/CTC/INE/2008 – p. 25/2
Download