Você está na página 1de 15

Desenvolvimento de software

Lógica de programação
É a razão que leva a encadear instruções (algoritimo) para resolver um problema
Algoritmo
Conjunto predeterminado e definido de passos para resolução de um problema
Linguagem de programação
Alto nível – mais distantes do código de máquina, mais próximas à linguagem natural
(JAVA, javascript, C)
Baixo Nível – mais próximas ao código de máquina, mais distantes da linguagem
natural (Assembly)
Lingiuagens e algoritimos
Código
Pseudocódigo
Fluxograma
Tipos elementares
Inteiros
Real
Caractere
Logico (booleano)
Tipo estruturados
Texto (cadeia de caracteres)
Arrays
Tipos definidos pelo usuário (receita, bolo, pessoa)
Entrada de dados input
Teclado
Mouse
Leitor de código de barras
Biometria
Saída de dados output
Tela
Impressora
Caixa de som
Catraca
Arquivo
Operadores
Operadores aritiméticos
Adição
Incremento Pós-fixado
Retorne o valor para a operação depois incremente a variável
Variável ++
X = 10
Y= X++
Imprime(y) --10
Imprime(X) --11
Incremento Pré- fixado
Incremente a variável depois retorne o valor
++ Variável
X = 10
Y= ++X
Imprime(y) -- 11
Imprime(X) -- 11
Subtração
Multiplicação
Divisão
Módulo (ou resto)
MOD ou %
2 mod 3 = 2
5 mod 6 = 5
...
4.5 mod 1.2 = 0.9
O quociente é que tem que ser natural, ou seja, 4.5/1.2 = 3 e sobra 0.9
Exponenciação
Operadores relacionais
Igual
Diferente
Menor que
Maior que
Maior igual a
Menor igual a
Operadores lógicos
E
Ou
Estrutura de controle
Decisão
Se então
Se senão
Caso
Repetição
Enquanto faça
Faça o teste e depois executa o comando
Faça enquanto
Executa o comando depois faça o teste
Para de ate faça
Faça o teste executa o comando e faça o incremento
Desvios incondicionais
Simplesmente direciona o código para outro ponto, sem nenhum teste
Podem ser de 3 tipos
Goto
Break
Interrompe o loop e vai para a linha seguinte
For var in sequence
If condition
Break
Sai da execução
Continue
Interrompe o loop e volta para o teste
For var in sequnce
If condition
Continue
Volta a executar o for
Recursividade
Direta
Se a função chama a si mesma no corpo da própria função
Indireta
Se a função chama outra (ou outras) que chamam a inicial
Passagem de parâmetro
Por valor
Passa uma cópia do valor
Alterações no valor não alteram o valor da variável original
Por referencia
Passa uma referência para a variável original
Alterações no valor alteram a variável original
Obs.:
Caso passe um ponteiro por valor
objeto {idade, nome}
objeto-> end1
idade-> end2
nome-> end3
Se passar objeto por valor para uma variável q
Q=objeto
Q{idade, nome}
q-> end4
No entanto idade e nome continuam apontando respectivamente para end2 e end3. Sendo
assim, alterações de idade e nome de q alteram também idade e nome de objeto
Se passar objeto por referência para uma variável q
Q=objeto
Q{idade, nome}
q-> end1
Sistema de numeração
Sistema binário
A parte inteira do número tem potências positivas e crescentes à medida em que o algarismo
aparece mais à esquerda, e negativas e decrescentes na parte fracionária. A decomposição do
número 1001,101 se dá da seguinte forma:
A parte inteira é, portanto, (8 + 1) = 9, e a parte fracionária (1/2 + 1/8) = 0,625. O número
1001,101 em binário é representado em decimal por 9,625. Conforme vimos em aula, a resposta
corresponde à letra E, ou seja, 1001,101 (base 2) é igual a 9,625 (base 10).
Sistema decimal
1994
1x10^3 + 9x10^2 + 9x10^1 + 4x10^0 = 1994
Sistema octal
3712
3x8^3 + 7x8^2 + 1x8^1 + 2x8^0 = 1994
Métodos de transformação
Resto da divisão por 2 para transformar 237 em binário
237/2 = 118 --- 1
118/2 = 59 --- 0
59/2 = 29 --- 1
29/2 = 14 --- 1
14/2 = 7 --- 0
7/2 = 3 --- 1
3/2 = 1 --- 1
1/2 = 0 --- 1
11101101 binário = 237 decimal
Transformar 11101101 para octal
011 --- 3
101 --- 5
101 --- 5
355 octal = 11101101 binário
Transformar 11101101 para hexadecimal (0,1,2,3,4,5,6,7,8,9,A,B,C,D,E,F)
1110 --- 14 --- E
1101 --- 13 --- D
ED hexadecimal = 11101101 binário
Compiladores
Fase de análise
Analise léxica
Formar tokens
Tabela de simbolos
Analise sintática
Estrutura do código, se os tokens estão na ordem correta
Arvore de analise
Análise semântica
Tem como objetivo verificar os inter-relacionamentos de um programa, validando tipologias,
fluxo de controle e unicidade na declaração de variáveis
Erros de tipo são verificados pelo analisador semântico, que integra o gerador de código
intermediário
Geração de código intermediário
otimização
Fase de síntese
Otimização
Geração de código final
Chama-se cruzado o compilador que gera um programa que seja executável em pelo
menos um sistema operacional diferente daquele onde o compilador tenha sido
executado
A tabela de símbolos utilizada no processo de compilação contém informações sobre
tipos e atributos de cada nome definido pelo usuário no programa. Essas informações
são colocadas na tabela de símbolos pelos analisadores léxico e sintático e usadas pelo
analisador semântico e pelo gerador de código
Compiladores
Momento 1
Condigo fonte -> transformação -> executável
Momento 2
Entradas -> executável -> saídas
Permitem a verificação de erros sintáticos e semânticos em tempo de compilação
Analisam o código todo durante o processo de compilação, antes de ser executado
Podem otimizar o código
Normalmente têm execução mais rápida
Normalmente são necessários em sistemas mais robustos, pois podem checar
dependências em tempo de compilação
Os executáveis são específicos para uma determinada plataforma/arquitetura
Modificações requerem a recompilação do código
Interpretadores
Condigo fonte e entradas -> interpretador -> saídas
Normalmente só conseguem fazer análise sintática antes da execução
Erros semânticos só são percebidos em tempo de execução
Executam 1 linha por vez
Os códigos-fontes normalmente menores que em sistema compilados
Normalmente são mais lentos, pois precisam realizar a transformação do código fonte
durante a execução
São independentes de plataforma/arquiteturas
Normalmente ambientes interpretados são mais fáceis de realizar mudanças, porém as
mudanças são mais propensas a erros
Pyton, java script, PHP
Ambientes híbridos
Momento 1
Condigo fonte -> transformação -> condigo intermediário (bytecode)
Momento 2
Condigo intermediário e entradas -> interpretador -> saídas
Diminuem o tempo de interpretação
Geram um código portável, porém mais próximo da linguagem de máquina
Podem se beneficiar de optimizações durante a compilação
JAVA é compilado e interpretado
Processo genérico de compilação
Codigo fonte (alto nível) -> Compilador -> assembly (baixo nível) -> motador ->
código objeto (código binário) -> ligador (linker) -> executável (modulo de carga) ->
carregador
Produtos de processo de compilação
Código fonte
Código próximo ao humano, com instruções de alto nível escritas pelo desenvolvedor
Código de montagem (assembly)
Código com a estrutura da máquina (baixo nível), porém sem instruções binárias
Código objeto
É o código de montagem onde as instruções e endereçamentos foram substituídos por seu
código binário específico da arquitetura de processador específica, mas que ainda pode conter
referências externas
Executável ou Módulo de Carga
É o código binário pronto para ser carregado em memória, com todas as referências externas
substituídas ou resolvidas
Programas do processo de compilação
Pré-processador
Processa um código-fonte mais primitivo gerando um outro código-fonte pronto para ser
compilado
Compilador
Transforma o código-fonte em código de montagem
Montador (assembler)
Transforma o código de montagem em código-objeto (binário)
Ligador (linker)
Resolve as referências do código-objeto, transformando-o em módulo e carga
Carregador (Loader)
Carrega o módulo de carga em memória e controla o endereçamento (em caso de
endereçamento relativo)
Pré-processador (tem em C e C++)
É um programa que PODE ser utilizado no processo de compilação para fazer
transformações no código-fonte como
Remoção de comentários
Inclusão de definições externas no conteúdo do arquivo
Substituições léxicas como troca de macros, inclusões condicionais etc.
Em C eram os famosos #DEFINE, #INCLUDE, #IFDEF, #UNDEF, etc.
Nas linguagens mais modernas, são cada dia menos utilizados
Compilador
São programas de computador que transformam um código-fonte escrito em uma
linguagem “alto nível” uma linguagem “baixo nível”
Código-Objeto: mais comum, já realizam o trabalho do montador
Linguagem de montagem: mais academicamente correto, ainda precisam ainda passar pelo
montador
Compiladores não geram o programa binário pronto para ser executado em memória
Montador (assembler)
É o processo de transformação de comandos de baixo nível para código-objeto (binário)
Linguagem de baixo nível -> estão próximas à forma de operar da máquina, mas ainda não são
instruções binárias
Código-objeto -> instruções binárias, que ainda podem ter referências externas
Existem diversos tipos de montadores: de um passo de passos, meta-assembler etc
Tipos de motadores
Cross-assembler
É executado em um computador com um processador diferente daquele para o qual se está
gerando código
Windows para ubunto
Macro-assembler
Dispõe de recursos de macro, efetuando a expansão do código cada vez que uma macro for
encontrada
Micro- assembler
Permite a escrita de micro-instruções, definindo-se assim um conjunto de instruções de um
processador microprogramável
Meta-assembler
É um assembler que pode montar programas para vários processadores diferentes
Assembler de um passo
Varre o programa-fonte apenas uma vez, gerando o código (deve existir alguma forma de se
resolver as referências adiante)
Assembler de dois passos
Varre o programa-fonte duas vezes para gerar o código, podendo assim resolver
automaticamente as referências adiante
Assembly vc assembler
Assembly
É o código de montagem, uma linguagem de programação específica de uma arquitetura de
processador
Assembler (montador/programa)
É o montador, o programa que processa o assembly (código de montagem) e produz o código-
objeto
Ligador (Linker) e bibliotecas
Ligador
É o responsável pela resolução de dependências internas e externar do código-objeto,
produzindo um código executável
Bibliotecas
São referências externas ao código-objeto, que podem ser estáticas ou dinâmicas
(compartilhadas)
Estáticas
Código da biblioteca é totalmente inserido no executável final (mais resiliente, menos
adaptável)
Dinâmicas
O binário apenas referencia a biblioteca (menos resiliente, mais adaptável)
Carregadores binários e realocáveis
É o responsável por carregar o código executável em memória, gerenciando as posições
de memória alocadas
Carregadores podem ser binários (fazem endereçamento estático), ou realocáveis
(endereçamento relativo)
Estático
O executável define a posição de memória que irá ocupar, que sempre será essa
Relativo
O executável define a posição relativa ao “zero do programa” (vai mudar de acordo com a
posição em que o programa for alocado na memória)
Fases do compilador
Análise (front-End)
É o momento em que acontece a análise “como está”, verificando apenas a coerência das
instruções, e transformando-as em código intermediário
Atividades
Análise Léxica
É o momento em que o texto de entrada é separado em palavras ou tokens, com o tipo do token,
o seu valor, e sua posição no fluxo
É montada a tabela de símbolos
São descartados os caracteres em branco, quebras de linhas e endentações
Nesse momento são identificados se foram utilizados caracteres inválidos, ou se os arquivos
foram corrompidos
Análise Sintática
É o momento de verificar se as palavras estão corretamente ordenadas, se o texto está
corretamente estruturado
Ex.: “IF” tem que ser seguido de uma condição, um”}” precisa estar depois de um “{”, o
operador “+” deve ter uma variável à esquerda e à direita
O analisador sintático também verifica se uma variável utilizada já foi definida
Erros sintáticos são sempre perceptíveis em tempo de compilação
Gera uma árvore de análise, colocando todas as operações e operandos
Análise semântica
É o momento de verificar se, apesar de sintaticamente correta, a expressão tem sentido
Ex.: atribuição de um numero inteiro para um de ponto flutuante
Toma a árvore de análise e verifica conta uma tabela de símbolos
Geração de código intermediário
A árvore de análise é transformada em uma representação de código próxima ao código de
montagem, mas cuja estruturação ainda permite manipulação
Sintese (back-end)
É o momento em que o código intermediário é otimizado e transformado no código final
(código de montagem)
Atividades
Otimização do código intermediário
Essa fase tenta identificar padrões otimizáveis no código, melhorando sua performance
Geração do código final
O código intermediário é traduzido para código de montagem
Alguns compiladores, nessa fase, já fazem a tradução para código-objeto, descartando a
necessidade de um montador
O código gerado, ainda que seja código-objeto, ainda não é considerado executável! O código
só será executável depois que o ligador resolver as dependências externas!
Diretiva é uma construção de algumas linguagens de programação que especifica como
o compilador ou montador deve processar o código fonte. Em alguns contextos, as
diretivas são conhecidas como programas.

Você também pode gostar