A apresentação está carregando. Por favor, espere

A apresentação está carregando. Por favor, espere

Introdução Analisar um algoritmo significa prever os recursos que o algoritmo necessitará. Podem ser recursos de memória, largura de banda, hardware ou.

Apresentações semelhantes


Apresentação em tema: "Introdução Analisar um algoritmo significa prever os recursos que o algoritmo necessitará. Podem ser recursos de memória, largura de banda, hardware ou."— Transcrição da apresentação:

1

2 Introdução Analisar um algoritmo significa prever os recursos que o algoritmo necessitará. Podem ser recursos de memória, largura de banda, hardware ou tempo. Podemos analisar O tempo de processamento em função de seus dados de entrada; A memória total utilizada pelo programa; O número de linhas do código do programa; Se o programa chega corretamente ao resultado; Se o programa é fácil de entender e de ser alterado; Se os erros causados por dados incorretos ou inesperados são tratados corretamente.

3 Entretanto uma análise detalhada da performance de um algoritmo, que leve em consideração todos esses fatores, é muito complicada e não muito significativa. De todos estes fatores tempo é o recurso mais freqüentemente medido. Em geral pela análise podemos indicar se um algoritmo é mais eficiente que o outro. Esta análise pode ser feita a partir de dois processos: pelo método empírico e pelo método analítico. Usar o método empírico possui os seguintes problemas: Os resultados são dependentes do compilador Os resultados são dependentes do hardware Quando grandes quantidades de memória são usadas os resultados podem depender deste aspecto Apesar dos problemas acima o método empírico é útil quando temos vários algoritmos distintos, que resolvem o mesmo problema, de mesma ordem de grandeza.

4 No método analítico procura-se determinar uma expressão que nos forneça o tempo de execução em função da quantidade de dados processados, isto é: Tempo = f(N) A complexidade de um algoritmo é o termo normalmente utilizado para se fazer referência à sua eficiência Para se encontrar a expressão que nos dá o tempo de execução de um algoritmo teremos que determinar a quantidade de operações que serão executadas para um conjunto de dados de tamanho N. Como exemplo, vamos determinar o tempo de execução para o cálculo do somatório de uma série aritmética simples:

5 1 I := 1; 2 Soma := 0; 3 while I <= N do begin 4 Soma := Soma + I; 5 I := I + 1; 6 end; Na análise do programa acima vamos considerar que os tempos necessários para realizar as operações de atribuição, comparação e adição são dados por T:=, T<= e T+, respectivamente.

6 Na análise anterior os tempos das operações depende dos fatores listados anteriormente. Dessa forma, fica bastante difícil comparar a eficiência de dois algoritmos usando esse mecanismo uma vez que teremos que especificar também o ambiente em que a medição foi feita. Para simplificar iremos usar um computador idealizado que executaria qualquer instrução em um mesmo tempo T. Em nosso modelo também não tentaremos modelar a hierarquia de memória. Esta análise convencional permite previsões excelentes do desempenho em máquinas reais. O efeito de tal simplificação resulta em que não precisamos mais considerar as operações separadamente. Dessa forma, para determinar o tempo de processamento de um programa basta simplesmente contar o número total de operações

7 Análise dos Tempos de Processamento Consideremos o problema de se determinar o maior valor de um vetor fazendo uma busca seqüencial no vetor: public class Max{ public static int max(int v[ ], int n){ int max = v[0]; for (int i = 1; i

8 Tempos de processamento do melhor caso, do pior caso e do caso médio Consideremos o problema de se determinar o maior valor de um vetor fazendo uma busca seqüencial no vetor: 1 max = A[0]; 2 i = 0; 3 while (i < N) { 4 if (A[i] > max) 5 max = A[i]; 6 i = i + 1; }

9 Agora surge um problema: quantas vezes a linha 5 será executada? Neste caso não sabemos pois depende dos valores existentes no vetor. O que fazer então? Três estratégias são adotadas: Determinar o tempo do pior caso Determinar o tempo do melhor caso Determinar o tempo do caso médio

10 O pior caso: Ordem crescente. Linha 5 é executada em todas as iterações do laço. Dessa forma, o tempo de processamento para o pior caso é dado por: T(N) = 5N + 3 O melhor caso: Ordem decrescente. Linha 5 nunca é executada. O tempo de processamento será então: T(N) = 4N + 3 O cálculo do tempo médio de processamento exige o prévio conhecimento da distribuição de probabilidades das diferentes entradas. Na maioria dos casos essa distribuição é desconhecida e freqüentemente é de tratamento matemático complexo. Como a análise do pior caso nos dá um limite superior do tempo de processamento, ela é a mais utilizada.

11 Exercício Considere o seguinte algoritmo soma = 0; 2 - for(x = 0; x < N; x++) 3 - { 4 - if (vetor[x] % 2 == 0) 5 - soma = soma + vetor[x]; 6 - } 7 - media = soma / N;

12 Exercício 2 Calcule, usando a simplificação vista, a complexidade do seguinte algoritmo 1 - for(x = 0; x < N-1; X++) 2 - for( y = 0; y < N; y++) 3 - if(vetor[x] > vetor[y]) 4 - { 5 - aux = vetor[x]; 6 - vetor[x] = vetor[y]; 7 - vetor[y] = aux; 8 - }

13 Notação O Quando estamos analisando a ordem de crescimento de um algoritmo normalmente estamos interessados em se ter uma idéia de como o método se comporta quando alteramos o valor de N. Para isso precisamos apenas analisar o termo de maior valor da expressão, ou seja o termo que cresce mais rápido. Exemplo: T(N) = N 2 +2N O termo representativo da expressão nos dá a sua ordem, sendo representado pela notação O, a qual é escrita colocando-se a letra O e, entre parênteses, o termo representativo da expressão.

14 Assim, o algoritmo acima seria expresso na notação O como sendo O(N 2 ), que se lê da seguinte forma: o algoritmo tem complexidade O(N 2 ) ou sua complexidade é de ordem N 2. A notação O pode ser derivada a partir de T(N) da seguinte maneira: Fazer o coeficiente de cada termo igual a um; Tomar o maior termo da função como sendo a ordem do algoritmo, descartando os termos restantes.

15 Normalmente dividem-se as complexidades dos algoritmos em sete categorias como mostradas na tabela abaixo:

16 Gráficos de cada complexidade em função de N Exemplo: Obtenha a notação O para:

17 Regras Para a Notação O A seguir apresentamos algumas regras simples para a determinação da complexidade do tempo de processamento de algumas composições básicas de comandos em um programa. Regra 1: Tempo constante A ordem de um algoritmo cujo tempo independe de N é constante e igual a O(1). Regra 2: Composição seqüencial O tempo de processamento para o pior caso de uma seqüência de comandos, tais como: S1; S2;... S3; é igual à ordem do maior tempo entre todos os comandos.

18 Regras Para a Notação O Regra 3: Iteração O tempo de processamento para o pior caso de um laço do tipo: for I := 1 to N S; é igual ao tempo de execução de S multiplicado pelo número de vezes que ele será executado no pior caso, isto é, a ordem é O(N x Ts(N)), onde Ts(N) é o tempo máximo de execução de S. Regra 4: Execução condicional O tempo de processamento para o pior caso de um comando if-then-else if S1 then S2 else S3; é igual ao maior tempo de execução entre os comandos S2 e S3.

19 Exemplo Seja o problema para calcular a série de somas S1, S2,..., Sn, obtidas por: cujo algoritmo é: 1 J := 1; 2 while J <= N do begin 3 S[J] := 0; 4 I := 1; 5 while I <= J do begin 6 S[J] := S[J] + A[I]; 7 I := I + 1; 8 end; 9 J := J + 1; 10 end;

20 Vejamos o cálculo da ordem do algoritmo:

21 Exercícios 1) Cada uma das seguintes fórmulas representa o número de operações de determinado algoritmo. Exprimir cada uma delas usando a notação O: a) n 2 + 5n b) 3n 2 + 5n c) (n + 7)(n – 2) d) 100n + 5 e) 6Log 2 N + 9 N f) 3N 4 + NLog2N g) 5N 2 + N 3/2

22 2) Escrever um trecho de programa contendo um laço para calcular a soma de todos os números inteiros de 1 a n. Fazer uma análise do tempo requerido, contando o número de somas e atribuições efetuadas e a seguir concluir qual a ordem do algoritmo. 3) Calcular a complexidade do seguinte trecho de programa: I := 1; while I <= N do begin J := 1; while J <= N do begin K := 1; while K <= N do begin Writeln(I, J, K); K := K + 1; end; J := J + 1; end; I := I + 1; end;


Carregar ppt "Introdução Analisar um algoritmo significa prever os recursos que o algoritmo necessitará. Podem ser recursos de memória, largura de banda, hardware ou."

Apresentações semelhantes


Anúncios Google