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

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

Aula 13 Tipos Abstractos de Dados IV. 2003/2004 Introdução à Programação 2 Estrutura global do programa (I) Construtores Inspectores.

Apresentações semelhantes


Apresentação em tema: "Aula 13 Tipos Abstractos de Dados IV. 2003/2004 Introdução à Programação 2 Estrutura global do programa (I) Construtores Inspectores."— Transcrição da apresentação:

1 Aula 13 Tipos Abstractos de Dados IV

2 2003/2004 Introdução à Programação 2 Estrutura global do programa (I) Construtores Inspectores

3 2003/2004 Introdução à Programação 3 Estrutura global do programa (II) Modificadores Auxiliares

4 2003/2004 Introdução à Programação 4 Estrutura global do programa (III) Operadores aritméticos não-membro

5 2003/2004 Introdução à Programação 5 Estrutura global do programa (IV) Operadores de igualdade e diferença não-membro

6 2003/2004 Introdução à Programação 6 TAD Racional (construtores)

7 2003/2004 Introdução à Programação 7 TAD Racional (inspectores)

8 2003/2004 Introdução à Programação 8 TAD Racional (modificadores)

9 2003/2004 Introdução à Programação 9 TAD Racional (modificadores)

10 2003/2004 Introdução à Programação 10 TAD Racional (implementação)

11 2003/2004 Introdução à Programação 11 Constantes de TAD Possível definir constantes de TAD: Racional const um_terço(1, 3); Mas é necessário ter alguns cuidados: cout << um_terço.numerador() << endl; Porque não Racional const um_terço(1 / 3); ? Dá erro!

12 2003/2004 Introdução à Programação 12 Constantes de TAD Compilador admite, por omissão, que as operações alteram a instância implícita Se a instância implícita for constante, não se podem invocar operações?? Podem, mas apenas as operações que declararem explicitamente que não alteram a instância implícita, pois a tratam como constante

13 2003/2004 Introdução à Programação 13 Operações que garantem constância: Sintaxe class Classe { … tipo operação(parâmetros) const; … }; tipo Classe::operação(parâmetros) const { … }

14 2003/2004 Introdução à Programação 14 Operações que garantem constância: Semântica Podem ser invocadas usando constantes: Classe const constante; constante.operação( argumentos ); Proibido para operações não constantes.

15 2003/2004 Introdução à Programação 15 Operações que garantem constância: Semântica Proibido!

16 2003/2004 Introdução à Programação 16 Operações que garantem constância: Semântica Métodos não-constantes *this é Classe& Métodos constantes *this é Classe const&

17 2003/2004 Introdução à Programação 17 TAD Racional (construtores) Construtores não podem ser const, pois instância implícita é por eles inicializada!

18 2003/2004 Introdução à Programação 18 TAD Racional (inspectores) Inspectores são sempre const ! Aos inspectores também se chama interrogações (queries)

19 2003/2004 Introdução à Programação 19 TAD Racional (modificadores)

20 2003/2004 Introdução à Programação 20 TAD Racional (modificadores) Modificadores nunca são const !

21 2003/2004 Introdução à Programação 21 TAD Racional (implementação)

22 2003/2004 Introdução à Programação 22 Métodos afectados … int Racional::numerador() const { … } int Racional::denominador() const { … } void Racional::escreve() const { … } … bool Racional::cumpreInvariante() const { … } …

23 2003/2004 Introdução à Programação 23 Métodos afectados void Racional::escreve() const { assert(cumpreInvariante()); cout << numerador(); if(denominador() != 1) cout << '/' << denominador(); assert(cumpreInvariante()); } Desnecessário! Num método constante, se o invariante se verifica no início (para a instância implícita), também se verifica no fim. (Hmmm… Há excepções. )

24 2003/2004 Introdução à Programação 24 Métodos afectados void Racional::escreve() const { assert(cumpreInvariante()); cout << numerador(); if(denominador() != 1) cout << '/' << denominador(); }

25 2003/2004 Introdução à Programação 25 Atenção! Utilização sistemática de const tem grandes vantagens: Obriga programador a pensar (menos erros) Programador explicita informação acerca do programa, que o compilador usa para detectar incoerências (erros detectados mais facilmente) Erros ocorrem mais cedo, durante compilação (erros detectados mais cedo)

26 2003/2004 Introdução à Programação 26 Desafio Quantas invocações de rotinas estão envolvidas em Racional r(1, 3); Racional s = r + 2; ignorando asserções? Dica: Quando se constrói um racional à custa de outro, é invocado um construtor por cópia, fornecido automaticamente pelo compilador, e que se limita a copiar os atributos um a um.

27 2003/2004 Introdução à Programação 27 Construtor Racional::Racional()

28 2003/2004 Introdução à Programação 28 Construtor Racional::Racional()

29 2003/2004 Introdução à Programação 29 Inspector Racional::numerador()

30 2003/2004 Introdução à Programação 30 Inspector Racional::denominador()

31 2003/2004 Introdução à Programação 31 Operador Racional::operator+=()

32 2003/2004 Introdução à Programação 32 Método auxiliar Racional::reduz()

33 2003/2004 Introdução à Programação 33 Operador Racional::operator+() Racional const operator+(Racional r1, Racional const& r2) { r1 += r2; return r1; }

34 2003/2004 Introdução à Programação 34 Operador Racional::operator==() bool operator==(Racional const& r1, Racional const& r2) { return r1.numerador() == r2.numerador() and r1.denominador() == r2.denominador(); }

35 2003/2004 Introdução à Programação 35 Traçado Racional r(1, 3); Racional s = r + 2; Número de invocações: 0

36 2003/2004 Introdução à Programação 36 Traçado Número de invocações: 1

37 2003/2004 Introdução à Programação 37 Traçado Número de invocações: 1

38 2003/2004 Introdução à Programação 38 Traçado Número de invocações: 1

39 2003/2004 Introdução à Programação 39 Traçado Número de invocações: 1

40 2003/2004 Introdução à Programação 40 Traçado Número de invocações: 1

41 2003/2004 Introdução à Programação 41 Traçado Número de invocações: 1

42 2003/2004 Introdução à Programação 42 Traçado Número de invocações: 2

43 2003/2004 Introdução à Programação 43 Traçado Número de invocações: 2

44 2003/2004 Introdução à Programação 44 Traçado int mdc(int const m, int const n) { … } Número de invocações: 3

45 2003/2004 Introdução à Programação 45 Traçado int mdc(int const m, int const n) { … } Número de invocações: 3

46 2003/2004 Introdução à Programação 46 Traçado Número de invocações: 3

47 2003/2004 Introdução à Programação 47 Traçado Número de invocações: 3

48 2003/2004 Introdução à Programação 48 Traçado Número de invocações: 3

49 2003/2004 Introdução à Programação 49 Traçado Número de invocações: 3

50 2003/2004 Introdução à Programação 50 Traçado Número de invocações: 3

51 2003/2004 Introdução à Programação 51 Traçado Racional r(1, 3); Racional s = r + 2; Número de invocações: 3

52 2003/2004 Introdução à Programação 52 Traçado Número de invocações: 4

53 2003/2004 Introdução à Programação 53 Traçado Número de invocações: 4

54 2003/2004 Introdução à Programação 54 Traçado Racional r(1, 3); Racional s = r + 2; Número de invocações: 4

55 2003/2004 Introdução à Programação 55 Traçado Racional const operator+(Racional r1, Racional const& r2) { r1 += r2; return r1; } Passagem por valor implica cópia! Número de invocações: 5

56 2003/2004 Introdução à Programação 56 Traçado Racional::Racional(Racional const& original) : numerador_(original.numerador_), denominador_(original.denominador_) { } Construtor por cópia fornecido automaticamente pelo compilador. Número de invocações: 6

57 2003/2004 Introdução à Programação 57 Traçado Racional::Racional(Racional const& original) : numerador_(original.numerador_), denominador_(original.denominador_) { } Número de invocações: 6

58 2003/2004 Introdução à Programação 58 Traçado Racional const operator+(Racional r1, Racional const& r2) { r1 += r2; return r1; } Número de invocações: 6

59 2003/2004 Introdução à Programação 59 Traçado Número de invocações: 7

60 2003/2004 Introdução à Programação 60 Traçado Número de invocações: 7

61 2003/2004 Introdução à Programação 61 Traçado Número de invocações: 8

62 2003/2004 Introdução à Programação 62 Traçado Número de invocações: 8

63 2003/2004 Introdução à Programação 63 Traçado Número de invocações: 8

64 2003/2004 Introdução à Programação 64 Traçado Número de invocações: 9

65 2003/2004 Introdução à Programação 65 Traçado Número de invocações: 9

66 2003/2004 Introdução à Programação 66 Traçado Número de invocações: 9

67 2003/2004 Introdução à Programação 67 Traçado Número de invocações: 10

68 2003/2004 Introdução à Programação 68 Traçado Número de invocações: 10

69 2003/2004 Introdução à Programação 69 Traçado Número de invocações: 10

70 2003/2004 Introdução à Programação 70 Traçado Número de invocações: 11

71 2003/2004 Introdução à Programação 71 Traçado Número de invocações: 11

72 2003/2004 Introdução à Programação 72 Traçado Número de invocações: 11

73 2003/2004 Introdução à Programação 73 Traçado Número de invocações: 11

74 2003/2004 Introdução à Programação 74 Traçado Número de invocações: 12

75 2003/2004 Introdução à Programação 75 Traçado Número de invocações: 12

76 2003/2004 Introdução à Programação 76 Traçado Número de invocações: 12

77 2003/2004 Introdução à Programação 77 Traçado Número de invocações: 12

78 2003/2004 Introdução à Programação 78 Traçado Número de invocações: 13

79 2003/2004 Introdução à Programação 79 Traçado Número de invocações: 13

80 2003/2004 Introdução à Programação 80 Traçado int mdc(int const m, int const n) { … } Número de invocações: 14

81 2003/2004 Introdução à Programação 81 Traçado int mdc(int const m, int const n) { … } Número de invocações: 14

82 2003/2004 Introdução à Programação 82 Traçado Número de invocações: 14

83 2003/2004 Introdução à Programação 83 Traçado Número de invocações: 14

84 2003/2004 Introdução à Programação 84 Traçado Número de invocações: 14

85 2003/2004 Introdução à Programação 85 Traçado Número de invocações: 14

86 2003/2004 Introdução à Programação 86 Traçado Número de invocações: 14

87 2003/2004 Introdução à Programação 87 Traçado Racional const operator+(Racional r1, Racional const& r2) { r1 += r2; return r1; } Devolução por valor implica cópia! Número de invocações: 14

88 2003/2004 Introdução à Programação 88 Traçado Racional::Racional(Racional const& original) : numerador_(original.numerador_), denominador_(original.denominador_) { } Número de invocações: 15

89 2003/2004 Introdução à Programação 89 Traçado Racional::Racional(Racional const& original) : numerador_(original.numerador_), denominador_(original.denominador_) { } Número de invocações: 15

90 2003/2004 Introdução à Programação 90 Traçado Racional r(1, 3); Racional s = r + 2; Número de invocações: 15

91 2003/2004 Introdução à Programação 91 Traçado Racional::Racional(Racional const& original) : numerador_(original.numerador_), denominador_(original.denominador_) { } Número de invocações: 16

92 2003/2004 Introdução à Programação 92 Traçado Racional::Racional(Racional const& original) : numerador_(original.numerador_), denominador_(original.denominador_) { } Número de invocações: 16

93 2003/2004 Introdução à Programação 93 Traçado Racional r(1, 3); Racional s = r + 2; // Fim! Número de invocações: 16

94 2003/2004 Introdução à Programação 94 Conclusão Há muito mais invocações do que suspeitávamos: 16! Cada invocação implica: Colocar endereço de retorno na pilha Construir parâmetros na pilha Executar corpo Destruir parâmetros da pilha Construir instância de devolução (se for o caso) Retornar ao local de invocação Ok, ok… Uma das cópias provavelmente não seria feita…

95 2003/2004 Introdução à Programação 95 Eficiência Dados Programa passa 80% do tempo em 20% do código 20% críticos desconhecidos a priori Conclusões Esforços de optimização antecipados são perda de tempo

96 2003/2004 Introdução à Programação 96 Mas… Há hábitos que contribuem para eficiência do programa e não têm qualquer desvantagem: 1. Usar passagem de argumentos por referência constante onde apropriado 2. Usar a palavra chave inline onde apropriado Já se lá irá, já se lá irá…

97 2003/2004 Introdução à Programação 97 Rotinas em-linha (inline) Corpo não existe num único local, sendo executado sempre que desejado Corpo é substituído pelo compilador em todos os locais onde a rotina é invocada Rotinas curtas e sem ciclos devem ser em- linha! Duas ou três linhas, digamos, excluindo asserções.

98 2003/2004 Introdução à Programação 98 Exemplo inline int soma(int const a, int const b) { return a + b; } int x1 = 10; int x2 = 30; int x3 = 50; int r = 0; int main() { r = soma(x1, x2); r = soma(r, x3); } int x1 = 10; int x2 = 30; int x3 = 50; int r = 0; int main() { r = x1 + x2; r = r + x3; } Geram mesmo código máquina! Usar variáveis globais é má ideia! Isto é só um exemplo!

99 2003/2004 Introdução à Programação 99 Exemplo em MAC-1 int soma(int const a, int const b) { return a + b; } int x1 = 10; int x2 = 30; int x3 = 50; int r = 0; int main() { r = soma(x1, x2); r = soma(r, x3); } jump main # Variáveis: x1 = 10 x2 = 30 x3 = 50 r = 0 # Aqui faz-se a soma: main: lodd x1 # Carrega variável x1 no acumulador. push # Coloca acumulador no topo da pilha. lodd x2 # Carrega variável x2 no acumulador. push # Coloca acumulador no topo da pilha. # Aqui a pilha tem os dois argumentos x1 e x2: call soma # Invoca a função soma. insp 2 # Repõe a pilha (limpeza da casa). # Aqui o acumulador tem o valor devolvido. stod r # Guarda o acumulador na variável r. lodd r # Carrega variável r no acumulador. push # Coloca acumulador no topo da pilha. lodd x3 # Carrega variável x3 no acumulador. push # Coloca acumulador no topo da pilha. # Aqui a pilha tem os dois argumentos r e x3: call soma # Invoca a função soma. insp 2 # Repõe a pilha (limpeza da casa). # Aqui o acumulador tem o valor devolvido. stod r # Guarda o acumulador na variável r. halt soma: lodl 2 addl 1 retn Sem inline (nem optimização). compilação

100 2003/2004 Introdução à Programação 100 jump main 10 30 50 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn ? ? ? ? ? ? ? ? soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 0 pc ? ac 100 sp 100 99 98 97 96 95 94 93 … pilha Instruções executadas: 0

101 2003/2004 Introdução à Programação 101 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 5 pc ? ac 100 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? ? ? ? … Instruções executadas: 1

102 2003/2004 Introdução à Programação 102 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 6 pc 10 ac 100 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? ? ? ? … Instruções executadas: 2

103 2003/2004 Introdução à Programação 103 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 7 pc 10 ac 99 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? ? ? … Instruções executadas: 3

104 2003/2004 Introdução à Programação 104 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 8 pc 30 ac 99 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? ? ? … Instruções executadas: 4

105 2003/2004 Introdução à Programação 105 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 1 addl 2 retn 30 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 9 pc 30 ac 98 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? ? … Instruções executadas: 5

106 2003/2004 Introdução à Programação 106 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 pc 30 ac 97 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 6

107 2003/2004 Introdução à Programação 107 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 21 pc 10 ac 97 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 7

108 2003/2004 Introdução à Programação 108 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 22 pc 40 ac 97 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 8

109 2003/2004 Introdução à Programação 109 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 10 pc 40 ac 98 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 9

110 2003/2004 Introdução à Programação 110 jump main 10 0 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 11 pc 40 ac 100 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 10

111 2003/2004 Introdução à Programação 111 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 12 pc 40 ac 100 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 11

112 2003/2004 Introdução à Programação 112 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 10 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 13 pc 40 ac 100 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 12

113 2003/2004 Introdução à Programação 113 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 14 pc 40 ac 99 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 13

114 2003/2004 Introdução à Programação 114 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 30 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 15 pc 50 ac 99 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 14

115 2003/2004 Introdução à Programação 115 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 10 50 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 16 pc 50 ac 98 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 15

116 2003/2004 Introdução à Programação 116 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 17 50 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 pc 50 ac 97 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 16

117 2003/2004 Introdução à Programação 117 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 17 50 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 21 pc 40 ac 97 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 17

118 2003/2004 Introdução à Programação 118 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 17 50 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 22 pc 90 ac 97 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 18

119 2003/2004 Introdução à Programação 119 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 17 50 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 17 pc 90 ac 98 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 19

120 2003/2004 Introdução à Programação 120 jump main 10 40 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 17 50 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 18 pc 90 ac 100 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 20

121 2003/2004 Introdução à Programação 121 jump main 10 90 lodd x1 push lodd x2 push call soma insp 2 stod r lodd r push lodd x3 push call soma insp2 stod r halt lodl 2 addl 1 retn 17 50 40 soma: 20 21 22 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 pc 90 ac 100 sp 100 99 98 97 96 95 94 93 30 50 ? ? ? ? ? … Instruções executadas: 21

122 2003/2004 Introdução à Programação 122 Exemplo em MAC-1 inline int soma(int const a, int const b) { return a + b; } int x1 = 10; int x2 = 30; int x3 = 50; int r = 0; int main() { r = soma(x1, x2); r = soma(r, x3); } jump main # Variáveis: x1 = 10 x2 = 20 x3 = 30 r = 0 # Aqui faz-se a soma: main: lodd x1 # Carrega variável x1 no acumulador. addd x2 # Adiciona variável x2 ao acumulador. stod r # Guarda o acumulador na variável r. lodd r # Carrega variável r no acumulador. addd x3 # Adiciona variável x3 ao acumulador. stod r # Guarda o acumulador na variável r. halt Com inline. compilação

123 2003/2004 Introdução à Programação 123 jump main 10 30 50 0 lodd x1 addd x2 stod r lodd r addd x3 stod r halt ? ? ? ? ? ? ? ? 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 0 pc ? ac 100 sp 100 99 98 97 96 95 94 93 … pilha Instruções executadas: 0

124 2003/2004 Introdução à Programação 124 jump main 10 30 50 0 lodd x1 addd x2 stod r lodd r addd x3 stod r halt ? ? ? ? ? ? ? ? 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 5 pc ? ac 100 sp 100 99 98 97 96 95 94 93 … Instruções executadas: 1

125 2003/2004 Introdução à Programação 125 jump main 10 30 50 0 lodd x1 addd x2 stod r lodd r addd x3 stod r halt ? ? ? ? ? ? ? ? 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 6 pc 10 ac 100 sp 100 99 98 97 96 95 94 93 … Instruções executadas: 2

126 2003/2004 Introdução à Programação 126 jump main 10 30 50 0 lodd x1 addd x2 stod r lodd r addd x3 stod r halt ? ? ? ? ? ? ? ? 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 7 pc 40 ac 100 sp 100 99 98 97 96 95 94 93 … Instruções executadas: 3

127 2003/2004 Introdução à Programação 127 jump main 10 30 50 40 lodd x1 addd x2 stod r lodd r addd x3 stod r halt ? ? ? ? ? ? ? ? 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 8 pc 40 ac 100 sp 100 99 98 97 96 95 94 93 … Instruções executadas: 4

128 2003/2004 Introdução à Programação 128 jump main 10 30 50 40 lodd x1 addd x2 stod r lodd r addd x3 stod r halt ? ? ? ? ? ? ? ? 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 9 pc 40 ac 100 sp 100 99 98 97 96 95 94 93 … Instruções executadas: 5

129 2003/2004 Introdução à Programação 129 jump main 10 30 50 40 lodd x1 addd x2 stod r lodd r addd x3 stod r halt ? ? ? ? ? ? ? ? 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 10 pc 90 ac 100 sp 100 99 98 97 96 95 94 93 … Instruções executadas: 6

130 2003/2004 Introdução à Programação 130 jump main 10 30 50 90 lodd x1 addd x2 stod r lodd r addd x3 stod r halt ? ? ? ? ? ? ? ? 0 x1: 1 x2: 2 x3: 3 r: 4 main: 5 6 7 8 9 10 11 pc 90 ac 100 sp 100 99 98 97 96 95 94 93 … Instruções executadas: 7 Sem inline eram 21…

131 2003/2004 Introdução à Programação 131 Comparação Sem inline : jump main # Variáveis: x1 = 10 x2 = 30 x3 = 50 r = 0 # Aqui faz-se a soma: main: lodd x1 # Carrega variável x1 no acumulador. push # Coloca acumulador no topo da pilha. lodd x2 # Carrega variável x2 no acumulador. push # Coloca acumulador no topo da pilha. # Aqui a pilha tem os dois argumentos x1 e x2: call soma # Invoca a função soma. insp 2 # Repõe a pilha (limpeza da casa). # Aqui o acumulador tem o valor devolvido. stod r # Guarda o acumulador na variável r. lodd r # Carrega variável r no acumulador. push # Coloca acumulador no topo da pilha. lodd x3 # Carrega variável x3 no acumulador. push # Coloca acumulador no topo da pilha. # Aqui a pilha tem os dois argumentos r e x3: call soma # Invoca a função soma. insp 2 # Repõe a pilha (limpeza da casa). # Aqui o acumulador tem o valor devolvido. stod r # Guarda o acumulador na variável r. halt soma: lodl 2 addl 1 retn Com inline : jump main # Variáveis: x1 = 10 x2 = 20 x3 = 30 r = 0 # Aqui faz-se a soma: main: lodd x1 # Carrega variável x1 no acumulador. addd x2 # Adiciona variável x2 ao acumulador. stod r # Guarda o acumulador na variável r. lodd r # Carrega variável r no acumulador. addd x3 # Adiciona variável x3 ao acumulador. stod r # Guarda o acumulador na variável r. halt Sempre mais rápido! Sempre mais curto? Não! Por vezes é mais longo. Depende da dimensão do código das rotinas, do número de invocações, etc. Código demasiado longo pode tornar a execução mais lenta, pois obriga a recorrer à memória virtual.

132 2003/2004 Introdução à Programação 132 Sintaxe Colocar a palavra chave inline antes do cabeçalho na definição da rotina: inline tipo nome(parâmetros) … { … } ou inline tipo Classe::nome(parâmetros) … { … }

133 2003/2004 Introdução à Programação 133 Estrutura global do programa (I) Construtores Inspectores

134 2003/2004 Introdução à Programação 134 Estrutura global do programa (II) Modificadores Auxiliares

135 2003/2004 Introdução à Programação 135 Estrutura global do programa (III) Operadores aritméticos não-membro

136 2003/2004 Introdução à Programação 136 Estrutura global do programa (IV) Operadores de igualdade e diferença

137 2003/2004 Introdução à Programação 137 Operadores em falta Aritméticos: Unários: + e - Relacionais: e >= Incrementação: Sufixo: ++ e -- Inserção e extracção de canais: > Começamos aqui. Fica por fazer...

138 2003/2004 Introdução à Programação 138 Incrementação prefixa class Racional { public: … /** Incrementa o racional. @pre *this = r. @post operator++ *this *this = r + 1. */ Racional& operator++(); … }; Racional& Racional::operator++() { assert(cumpreInvariante()); numerador_ += denominador(); assert(cumpreInvariante()); return *this; }

139 2003/2004 Introdução à Programação 139 Incrementação sufixa ?

140 2003/2004 Introdução à Programação 140 Incrementação sufixa: a solução /** Incrementa o racional, devolvendo o seu valor antes de incrementado. @pre r = r. @post operator++ = r r = r + 1. */ inline Racional const operator++(Racional& r, int) { Racional const cópia = r; ++r; return cópia; } Devolve-se por valor um racional com o valor antes de incrementado, i.e., devolve-se a cópia do racional r. Faz-se uma cópia de r antes de se incrementar, recorrendo à incrementação prefixa, já definida. Aha! Cá está a diferença! Trata-se o operador como se fosse binário, recebendo como argumento um inteiro com valor não especificado e irrelevante.

141 2003/2004 Introdução à Programação 141 Decrementação sufixa: a solução /** Decrementa o racional, devolvendo o seu valor antes de decrementado. @pre r = r. @post operator-- = r r = r - 1. */ inline Racional const operator--(Racional& r, int) { Racional const cópia = r; --r; return cópia; }

142 2003/2004 Introdução à Programação 142 Operador - unário: operação /** … */ class Racional { public: … /** Devolve simétrico do racional. @pre V. @post operator- = - *this. */ Racional const operator-() const; … private: … };

143 2003/2004 Introdução à Programação 143 Operador - unário: método inline Racional const Racional::operator-() const { assert(cumpreInvariante()); Racional r; r.numerador_ = -numerador(); r.denominador_ = denominador(); assert(r.cumpreInvariante()); return r; } Não é fundamental usar uma rotina membro, mas permite código mais eficiente, pois pode-se mudar o sinal do numerador directamente, evitando-se invocações espúrias do redutor de fracções.

144 2003/2004 Introdução à Programação 144 Operador + unário /** Devolve o racional. @pre V. @post operator+ r. */ inline Racional const& operator+(Racional const& r) { return r; }

145 2003/2004 Introdução à Programação 145 Operador < /** Devolve verdadeiro se o primeiro racional for menor que o segundo. @pre V. @post operator< = r1 < r2. */ inline bool operator<(Racional const& r1, Racional const& r2) { return r1.numerador() * r2.denominador() < r2.numerador() * r1.denominador(); } Como 0 < r1.d 0 < r2.d, r1.n / r1.d < r2.n / r2.d r1.n x r2.d < r2.n * r1.d

146 2003/2004 Introdução à Programação 146 Operadores e >= Podem-se definir à custa do operador < Como?

147 2003/2004 Introdução à Programação 147 Operador > /** Devolve verdadeiro se o primeiro racional for maior que o segundo. @pre V. @post operator> = r1 > r2. */ inline bool operator>(Racional const& r1, Racional const& r2) { return r2 < r1; }

148 2003/2004 Introdução à Programação 148 Operador <= /** Devolve verdadeiro se o primeiro racional for menor ou igual ao segundo. @pre V. @post operator<= = r1 <= r2. */ inline bool operator<=(Racional const& r1, Racional const& r2) { return not (r1 > r2); }

149 2003/2004 Introdução à Programação 149 Operador >= /** Devolve verdadeiro se o primeiro racional for menor ou igual ao segundo. @pre V. @post operator>= = r1 >= r2. */ inline bool operator>=(Racional const& r1, Racional const& r2) { return not (r1 < r2); }

150 2003/2004 Introdução à Programação 150 Outro desafio (fácil) Definir o operador == à custa do operador <

151 2003/2004 Introdução à Programação 151 Último problema Operador /= usa o operador !=, definido mais tarde Melhor solução: concentrar declarações de rotinas não-membro após definição da classe Definir rotinas não-membro mais tarde

152 2003/2004 Introdução à Programação 152 Preâmbulo e definição da classe C++ #include using namespace std; /** Devolve o máximo divisor comum dos inteiros passados como argumento. @pre m 0 ou n 0. @post mdc = mdc( m, n ). */ int mdc(int const m, int const n) { … } class Racional { … };

153 2003/2004 Introdução à Programação 153 Declaração de rotinas não-membro (I) /** Incrementa o racional, devolvendo o seu valor antes de incrementado. @pre r = r. @post operator++ = r r = r + 1. */ Racional const operator++(Racional& r, int); /** Decrementa o racional, devolvendo o seu valor antes de decrementado. @pre r = r. @post operator-- = r r = r - 1. */ Racional const operator--(Racional& r, int); Incrementação e decrementação sufixas

154 2003/2004 Introdução à Programação 154 Declaração de rotinas não-membro (II) /** Produto de dois racionais. @pre V. @post operator* = r1 × r2. */ Racional const operator*(Racional r1, Racional const& r2); /** Divisão de dois racionais. @pre r2 0. @post operator/ = r1 / r2. */ Racional const operator/(Racional r1, Racional const& r2); /** Soma de dois racionais. @pre V. @post operator+ = r1 + r2. */ Racional const operator+(Racional r1, Racional const& r2); /** Subtracção de dois racionais. @pre V. @post operator- = r1 - r2. */ Racional const operator-(Racional r1, Racional const& r2); Operadores aritméticos binários

155 2003/2004 Introdução à Programação 155 Declaração de rotinas não-membro (III) /** Devolve o racional. @pre V. @post operator+ r. */ Racional const& operator+(Racional const& r); /** Indica se dois racionais são iguais. @pre V. @post operator== = ( r1 = r2 ). */ bool operator==(Racional const& r1, Racional const& r2); /** Indica se dois racionais são diferentes. @pre V. @post operator!= = ( r1 r2 ). */ bool operator!=(Racional const& r1, Racional const& r2); Operadores de igualdade e diferença Operador identidade

156 2003/2004 Introdução à Programação 156 Declaração de rotinas não-membro (IV) /** Devolve verdadeiro se o primeiro racional for menor que o segundo. @pre V. @post operator< = r1 < r2. */ bool operator<(Racional const& r1, Racional const& r2); /** Devolve verdadeiro se o primeiro racional for maior que o segundo. @pre V. @post operator> = r1 > r2. */ bool operator>(Racional const& r1, Racional const& r2); /** Devolve verdadeiro se o primeiro racional for menor ou igual ao segundo. @pre V. @post operator<= = r1 <= r2. */ bool operator<=(Racional const& r1, Racional const& r2); /** Devolve verdadeiro se o primeiro racional for maior ou igual ao segundo. @pre V. @post operator>= = r1 >= r2. */ bool operator>=(Racional const& r1, Racional const& r2); Operadores relacionais

157 2003/2004 Introdução à Programação 157 Definição de métodos (I) Construtores Inspectores Modificadores Auxiliares

158 2003/2004 Introdução à Programação 158 Definição de rotinas não-membro inline Racional const operator++(Racional& r, int) { … } inline Racional const operator--(Racional& r, int) { … } inline Racional const operator*(Racional r1, Racional const& r2) { … } inline Racional const operator/(Racional r1, Racional const& r2) { … } inline Racional const operator+(Racional r1, Racional const& r2) { … } inline Racional const operator-(Racional r1, Racional const& r2) { … } inline Racional const& operator+(Racional const& r) { … } inline bool operator==(Racional const& r1, Racional const& r2) { … } inline bool operator!=(Racional const& r1, Racional const& r2) { … } inline bool operator<(Racional const& r1, Racional const& r2) { … } inline bool operator>(Racional const& r1, Racional const& r2) { … } inline bool operator<=(Racional const& r1, Racional const& r2) { … } inline bool operator>=(Racional const& r1, Racional const& r2) { … } int main() { … } Operadores aritméticos binários Incrementação e decrementação sufixas Operadores de igualdade e diferença Operador identidade Operadores relacionais

159 2003/2004 Introdução à Programação 159 TAD Racional (construtores)

160 2003/2004 Introdução à Programação 160 TAD Racional (inspectores)

161 2003/2004 Introdução à Programação 161 TAD Racional (inspectores)

162 2003/2004 Introdução à Programação 162 TAD Racional (modificadores)

163 2003/2004 Introdução à Programação 163 TAD Racional (modificadores)

164 2003/2004 Introdução à Programação 164 TAD Racional (implementação)

165 2003/2004 Introdução à Programação 165 Aula 13: Sumário Definindo constantes de uma classe: Necessidade de declarar operações como constantes (que não alteram a instância implícita). Sintaxe. Devolução por valor constante. Vantagens da utilização de const. Evitando o mecanismo de invocação de rotinas no código máquina produzido pelo compilador: Rotinas inline. Sintaxe. Regras de utilização. Explicação do efeito de inline sobre o código máquina produzido. Exemplo com programa em C++ e respectiva tradução para MAC-1 (ver Arquitectura de Computadores). Quando optimizar. Incrementação e decrementação sufixa: sobrecarga. Ordem de declaração/definição de operações/métodos e rotinas não-membro associados a um TAD.


Carregar ppt "Aula 13 Tipos Abstractos de Dados IV. 2003/2004 Introdução à Programação 2 Estrutura global do programa (I) Construtores Inspectores."

Apresentações semelhantes


Anúncios Google