Mudanças entre as edições de "PRG-2011-1-sobral"

De MediaWiki do Campus São José
Ir para navegação Ir para pesquisar
 
(115 revisões intermediárias por 2 usuários não estão sendo mostradas)
Linha 7: Linha 7:
 
<br>''Skype'': mm-sobral
 
<br>''Skype'': mm-sobral
 
<br>''Lista de email (forum)'': [http://groups.google.com/group/prg-ifsc prg-ifsc@googlegroups.com]
 
<br>''Lista de email (forum)'': [http://groups.google.com/group/prg-ifsc prg-ifsc@googlegroups.com]
<br>''Atendimento paralelo'': 2a feira 10h - 11 h, 3a feira 10h - 12 h ou 16h - 17 h, 5a feira 16h - 17h (no Laboratório de Desenvolvimento de Tele)
+
<br>''Atendimento paralelo'': 4a feira 10:00 - 11:30 h, 5a feira 8:00 - 9:30 h e 13:30 - 15:30 h (no Laboratório de Desenvolvimento de Tele)
 
<br>''Reavaliação (recuperação)'': no final do semestre
 
<br>''Reavaliação (recuperação)'': no final do semestre
 +
<br> '''IMPORTANTE:''' o direito de recuperar uma avaliação em que se faltou somente existe mediante justificativa reconhecida pela coordenação. Assim, deve-se protocolar a justificativa no prazo de 48 horas, contando da data e horário da avaliação, e aguardar o parecer da coordenação. O não cumprimento desse procedimento implica a impossibilidade de fazer a recuperação, e assim a reprovação na disciplina.
  
* [http://www.sj.ifsc.edu.br/~msobral/SOP/plano.html Plano da disciplina]
+
* [http://tele.sj.ifsc.edu.br/~msobral/SOP/plano.html Plano da disciplina]
 
* [[Sistemas_Operacionais_e_Introdu%C3%A7%C3%A3o_a_Programa%C3%A7%C3%A3o|Ementa e bibliografia]]
 
* [[Sistemas_Operacionais_e_Introdu%C3%A7%C3%A3o_a_Programa%C3%A7%C3%A3o|Ementa e bibliografia]]
  
 
== Softwares ==
 
== Softwares ==
  
Será usado como plataforma de estudo o sistema operacional Ubuntu Linux 10.04 LTS. Para obtê-lo há essas opções:
+
Será usado como plataforma de estudo o sistema operacional Ubuntu Linux 10.04 LTS ou posterior. Para obtê-lo há essas opções:
  
 
# Trazer um CD-R virgem para que eu faça a cópia aqui no IFSC
 
# Trazer um CD-R virgem para que eu faça a cópia aqui no IFSC
Linha 26: Linha 27:
  
 
== Listas de exercícios ==
 
== Listas de exercícios ==
 
* [http://www.sj.ifsc.edu.br/~msobral/SOP/listas/lista1-2010-2.pdf 1a lista (parte teórica)]
 
* [http://www.sj.ifsc.edu.br/~msobral/SOP/listas/lista1-pratica-2010-2.pdf 1a lista (parte prática)]
 
  
 
== Referências adicionais ==
 
== Referências adicionais ==
  
* [[Sistemas Operacionais e Introdução a Programação (diário 2010-1) - Prof. Tiago Semprebom|Diário de aula do Prof. Tiago Semprebom]]
+
* [[PRG-2011-1-tiago|Diário de aula do Prof. Tiago Semprebom]]
* [http://www.sj.ifsc.edu.br/~msobral/SOP/ Antiga página da disciplina (2009-2)]
+
* [http://tele.sj.ifsc.edu.br/~msobral/SOP/ Antiga página da disciplina (2009-2)]
 
* Valle, Odilson Tadeu.  [[Media:Gerencia_de_redes.pdf|Gerência de Redes]]. IFSC - Unidade São José. 2009. ''(ver capítulos 1 a 9)''
 
* Valle, Odilson Tadeu.  [[Media:Gerencia_de_redes.pdf|Gerência de Redes]]. IFSC - Unidade São José. 2009. ''(ver capítulos 1 a 9)''
 
* [https://help.ubuntu.com/community Ubuntu Documentation]
 
* [https://help.ubuntu.com/community Ubuntu Documentation]
Linha 40: Linha 38:
 
* Demais referências contidas na [[Sistemas Operacionais e Introdução a Programação (página)#Sobre_a_Disciplina|página principal de SOP]].
 
* Demais referências contidas na [[Sistemas Operacionais e Introdução a Programação (página)#Sobre_a_Disciplina|página principal de SOP]].
  
= Sistemas operacionais =
+
= Aulas =
 
 
== 16/03: Apresentação ==
 
  
Apresentação da disciplina: plano de ensino, avaliação, abordagem pedagógica.
+
== 16/03: Introdução ==
  
== 17/03: Introdução ==
+
'''Apresentação da disciplina:''' plano de ensino, avaliação, abordagem pedagógica.
  
'''Assuntos:''' Lógica de programação: instrução, sequência lógica, algoritmo.
+
'''Assunto:''' Lógica de programação
  
 
''Referências auxiliares:''
 
''Referências auxiliares:''
Linha 59: Linha 55:
  
 
''Videos sobre algoritmos:''
 
''Videos sobre algoritmos:''
* [http://www.youtube.com/watch?v=k0xgjUhEG3U Outro algoritmo ...]
 
 
* [http://www1.folha.uol.com.br/folha/videocasts/ult10038u689083.shtml Resolvendo o cubo de Rubik (cubo mágico)]
 
* [http://www1.folha.uol.com.br/folha/videocasts/ult10038u689083.shtml Resolvendo o cubo de Rubik (cubo mágico)]
 
** [http://www.sj.ifsc.edu.br/~msobral/SOP/coisas/1285780.flv Cópia desse vídeo aqui no Ifsc]
 
** [http://www.sj.ifsc.edu.br/~msobral/SOP/coisas/1285780.flv Cópia desse vídeo aqui no Ifsc]
 
+
* [http://www.youtube.com/watch?v=k0xgjUhEG3U Outro algoritmo ...]
'''Exemplificando com ''shell scripts'':'''
 
 
 
<syntaxhighlight lang=bash>
 
#!/bin/bash
 
 
 
# Cada linha no script abaixo corresponde a uma instrução ...
 
# O conjunto de instruções na ordem apresentada forma uma sequência lógica ...
 
 
 
echo Iniciando o script ...
 
echo Vou procurar todos os arquivos de texto existentes neste diretório
 
 
 
find . -type f -name "*.doc" > .tmp
 
find . -type f -name "*.txt" >> .tmp
 
find . -type f -name "*.rtf" >> .tmp
 
find . -type f -name "*.odt" >> .tmp
 
 
 
echo Os arquivos são:
 
 
 
cat .tmp
 
 
 
rm -f .tmp
 
</syntaxhighlight>
 
  
 
=== Problemas exemplo ===
 
=== Problemas exemplo ===
Linha 92: Linha 65:
 
Há três recipientes com tamanhos distintos: um com 8 litros, outro com 5 litros e o terceiro com 3 litros. O recipiente com 8
 
Há três recipientes com tamanhos distintos: um com 8 litros, outro com 5 litros e o terceiro com 3 litros. O recipiente com 8
 
litros está completamente cheio. Deseja-se colocar 4 litros em dois recipientes. Considere que os recipientes não são graduados.
 
litros está completamente cheio. Deseja-se colocar 4 litros em dois recipientes. Considere que os recipientes não são graduados.
 
  
 
'''Problema da travessia'''
 
'''Problema da travessia'''
Linha 109: Linha 81:
  
 
Qual a sequência de operações para mover os discos de uma haste para outra ?
 
Qual a sequência de operações para mover os discos de uma haste para outra ?
 
=== Atividade extra ===
 
 
* O jogo [http://armorgames.com/play/2205/light-bot LightBot] mostra de uma forma divertida como criar pequenos algoritmos. Até que fase desse jogo você consegue chegar ?
 
  
 
=== Leitura adicional ===
 
=== Leitura adicional ===
Linha 119: Linha 87:
 
* [http://en.wikipedia.org/wiki/Algorithm Uma definição de algoritmos na Wikipedia]
 
* [http://en.wikipedia.org/wiki/Algorithm Uma definição de algoritmos na Wikipedia]
  
== 23/04: Algoritmos ==
+
== 17/03: Algoritmos ==
  
Ver [http://www.sj.ifsc.edu.br/~msobral/SOP/slides/aula11.pdf transparências].
+
Para criar algoritmos, deve-se primeiro entender o que são instruções e sequências lógicas;
  
Introdução a lógica de programação:
+
O jogo [http://armorgames.com/play/2205/light-bot LightBot] mostra de uma forma divertida como criar pequenos algoritmos. Nesse jogo o robô deve se movimentar de acordo com uma '''sequência''' de '''instruções elementares''' definidas pelo jogador. Apesar de sua simplicidade, ele pode se tornar bastante desafiador ! Até que fase desse jogo você consegue chegar ?
* '''Algoritmos:''' sequência finita de passos que leva à execução de uma tarefa. Exemplos:
 
*# [http://unesp.br/~jroberto/rubiks Como resolver o cubo de Rubik (cubo mágico)]
 
*# ''Cálculo das raízes de uma equação de 2o grau (método de Baskara)''
 
*# [http://www.sj.ifsc.edu.br/~msobral/SOP/slides/pao.png Receita de pão]
 
*# ''Soma de dois números:'' <syntaxhighlight lang=text>
 
Ler primeiro número
 
Ler segundo número
 
Somar os dois números lidos
 
Mostrar o resultado
 
</syntaxhighlight>
 
* '''Programa:''' tradução de um algoritmo para uma linguagem de programação, para que possa ser executado por um computador.
 
*# ''Soma de dois números em shell script:'' <syntaxhighlight lang=bash>
 
#!/bin/bash
 
  
echo -n Entre com o primeiro numero:
+
[[imagem:Lightbot.png]]
read x
 
echo -n Entre com o segundo numero:
 
read y
 
z=$(($x + $y))
 
  
echo A soma de $x e $y eh $z
+
=== Desenhando figuras geométricas ===
</syntaxhighlight> Para executar esse programa, grave-o em um arquivo chamado ''soma.sh'' e em seguida faça o seguinte: <syntaxhighlight lang=bash>
 
bash soma.sh
 
</syntaxhighlight>
 
*# ''Soma de dois números em Linguagem C:'' <syntaxhighlight lang=c>
 
#include <stdio.h>
 
  
int main() {
+
# [http://scratch.mit.edu/ Scratch] é um software educacional para ajudar no ensino de matemática, geometria e introdução à programação. Com ele pequenos programas podem ser escritos de foram visual, com instruções representadas por blocos que se encaixam como Lego. Ele possibilita fazer desenhos facilmente, seguindo um programa com instruções de desenho. Use-o para desenhar estas figuras:
  int x, y, r;
+
#* triângulo equilátero
 +
#* triângulo isósceles
 +
#* quadrado
 +
#* hexágono
 +
#* quadrado com vértices interligados
 +
#* Um círculo
  
 +
[[imagem:Scratch.png]]
  
  printf("Entre com o primeiro numero: ");
 
  scanf("%d", &x);
 
  
  printf("Entre com o segundo numero: ");
+
* Agora tente algo mais avançado:
  scanf("%d", &y);
+
** Desenhe um triângulo equilátero, porém perguntando na tela qual o tamanho do lado.
 +
** repita o desenho do triângulo, porém fazendo-o lentamente: espere 1 segundo após desenhar cada lado do triângulo.
 +
** Faça com que um pequeno traço se movimente de um lado a outro do palco.
 +
** Faça com que um pequeno traço se movimente em círculo indefinidamente.
 +
** Faça com que uma bola role pela horizontal. Insira quatro raios na bola para ajudar no efeito visual de movimento.
  
  r = x + y;
+
=== Atividade para casa ===
  
  printf("A soma de %d e %d eh %d\n", x, y, r);
+
Faça as figuras geométricas indicadas na aula !
  
  return 0;
+
== 23/03: Começando os primeiros algoritmos ... ==
}
 
</syntaxhighlight> Para executar esse programa, grave-o em um arquivo chamado ''soma.c'' e em seguida faça o seguinte: <syntaxhighlight lang=bash>
 
gcc -o soma soma.c
 
./soma
 
</syntaxhighlight>
 
*# ''Soma de dois números em Java:'' <syntaxhighlight lang=java>
 
import java.util.Scanner;
 
  
class Soma
+
'''Algoritmo''' é uma sequência lógica de instruções, a qual possui um início e um fim.
 
        public static void main(String args[])
 
        {
 
  int  x, y, r;
 
  Scanner scanner = new Scanner(System.in);
 
 
          System.out.print("Entre com o primeiro numero: ");
 
  x = scanner.nextInt();
 
  
          System.out.print("Entre com o segundo numero: ");
+
'''Sequência lógica''' é uma  sequência correta de instruções capaz de gerar o resultado esperado.
  y = scanner.nextInt();
 
  
  r = x + y;
 
  
  System.out.println("A soma de " + x + " e " + y + " eh " + r);
+
A escrita ou projeto de algoritmos se faz com:
        }
+
* ''Estruturas de controle:'' comandos que modificam  uma sequência de instruções
}
+
* ''Estruturas de dados:'' dados (valores) usados e modificados durante a execução do algoritmo.
</syntaxhighlight>Para executar esse programa, grave-o em um arquivo chamado ''Soma.java'' e em seguida faça o seguinte: <syntaxhighlight lang=bash>
 
javac Soma.java
 
java Soma
 
</syntaxhighlight>
 
*# ''Soma de dois números em Python:'' <syntaxhighlight lang=python>
 
#!/usr/bin/python
 
  
import sys
 
  
print "Entre com o primeiro numero: ",
+
Para introduzir esses conceitos, nada melhor que um  pequeno projeto ...
x = int(sys.stdin.readline())
 
  
print "Entre com o segundo numero: ",
 
y = int(sys.stdin.readline())
 
  
r = x + y
+
=== Projeto: um jogo muito simples ===
  
print "A soma de", x, "e", y, "eh", r
+
Você conhece o jogo clássico [http://pt.wikipedia.org/wiki/Space_Invaders Space Invaders] ?
  
sys.exit(0)
+
[[imagem:Spaceinvaders.jpg]]
</syntaxhighlight>Para executar esse programa, grave-o em um arquivo chamado ''soma.py'' e em seguida faça o seguinte: <syntaxhighlight lang=bash>
 
python soma.py
 
</syntaxhighlight>
 
  
Como mostrado acima, o mesmo algoritmo foi traduzido para programas em diferentes linguagens de programação. Ao serem executados, geraram o mesmo resultado.
 
  
=== Exercícios: desenho de figuras geométricas ===
+
Pros padrões atuais esse é um jogo muito simples. Você conseguiria reproduzi-lo, mesmo que simplificado, no Scratch ? Ele poderia começar assim:
  
# Usando apenas as instruções: <syntaxhighlight lang=text>
+
[[imagem:Jogo1-scratch.gif]]
acendeCaneta
 
apagaCaneta
 
avança X
 
giraDireita angulo
 
giraEsquerda angulo
 
fazArco X graus, raio Y
 
</syntaxhighlight> escreva algoritmos para desenhar a figura entregue pelo professor. Não mostre sua figura para as outras equipes.
 
# [http://edu.kde.org/kturtle/ kturtle] é um software educacional para ajudar no ensino de matemática, geometria e introdução à programação. Ele possibilita fazer desenhos facilmente, seguindo um programa com instruções de desenho. Usando as instruções: <syntaxhighlight lang=bash>
 
reset (move a tartaruga para o centro da tela)
 
clear (limpa a tela)
 
pendown (põe a caneta no papel - acendeCaneta)
 
penup (levanta a caneta - apagaCaneta)
 
forward X (avança X posições)
 
turnright angulo (gira pra direita)
 
turnleft angulo (gira pra esquerda)
 
</syntaxhighlight> ... escreva programas para os algoritmos criados no ítem  anterior.<br><br>[http://docs.kde.org/stable/pt/kdeedu/kturtle/reference.html Guia de referência completo do Kturtle]
 
# Usando o '''kturtle''' escreva algoritmos para desenhar as seguintes figuras:
 
#* triângulo equilátero
 
#* triângulo isósceles
 
#* triângulo escaleno
 
#* quadrado
 
#* hexágono
 
#* octógono
 
#* quadrado com vértices interligados
 
#* Um círculo
 
#* 7 hexágonos interligados (um central e seis periféricos).
 
#* 7 círculos interligados (um central e seis periféricos), parecendo uma flor
 
# Fractais são figuras nas quais cada pedacinho é semelhante à toda figura. Um fractal  bastante simples de criar é o Floco de Neve Koch, cuja criação pode ser entendida na sequência de  figuras abaixo:
 
  
[[imagem:Koch0.png]]
 
<br>''Primeira iteração''
 
  
[[imagem:Koch1.png]]
+
# O robô se movimenta na horizontal, comandado pelas teclas ''seta pra direita'' e ''seta pra esquerda''.
<br>''Segunda iteração''
+
# O helicóptero se movimenta de um lado a outro constantemente, refletindo  nas bordas.
 +
# Ao teclar espaço,  um tiro sai do robô em direção ao topo do palco
 +
# Se o tiro acertar o helicóptero, o jogo termina.
  
[[imagem:Koch2.png]]
 
<br>''Terceira iteração''
 
  
[[imagem:Koch3.png]]
+
O que você precisa para fazer esse jogo ?
<br>''Próximas iterações''
+
# Movimento do helicóptero.
 +
# Movimento do robô comandado pelo teclado.
 +
# Acionamento do tiro.
 +
# Detecção se o tirou acertou o helicóptero.
  
Usando o '''kturtle''' desenhe essas figuras, reproduzindo o maior número de iterações que conseguir. Você consegue descobrir uma  regra para gerá-las ?
+
'''Mãos à obra !'''
  
''Obs: [http://pt.wikibooks.org/wiki/Matem%C3%A1tica_divertida/Fractais_e_o_infinitamente_pequeno#Fractais fonte dessas figuras]''
+
== 24/03: Introduzindo algoritmos: variáveis e expressões ==
  
==== Dicas para o kturtle ====
+
Variáveis são usadas em algoritmos para guardar dados. Dados podem ser:
 +
* Números inteiros ou reais
 +
* Letras ou textos
 +
* Valores lógicos (booleanos)
 +
* ... e outros que vocês descobrirão futuramente !
  
# Pode-se repetir uma sequência de instruções usando-se o comando ''repeat''. Por exemplo, para desenhar um pentágono usando ''repeat'': <syntaxhighlight lang=text>
+
Uma variável possui um identificador, que nada mais é que seu nome. No Scratch as variáveis são criadas e podem ser modificadas com os comandos categorizados em ''Variáveis'' (comandos laranjas):
repeat 5 {
 
  forward 50
 
  turnleft 72
 
}
 
</syntaxhighlight>
 
# Podem-se usar variáveis para generalizar os algoritmos. Uma variável tem um identificador, que deve ser precedido do caractere ''$'': <syntaxhighlight lang=text>
 
$x=5
 
$lado=50
 
repeat $x {
 
  forward $lado
 
  turnleft 360/$x
 
}
 
</syntaxhighlight>
 
# Pode-se usar o comando ''ask'' para ler do teclado valores a serem usados no algoritmo de desenho: <syntaxhighlight lang=text>
 
$x = ask "Quantos lados tem o polígono ?"
 
$lado = ask "Qual o comprimento de cada lado ?"
 
repeat $x {
 
  forward $lado
 
  turnleft 360/$x
 
}
 
</syntaxhighlight>
 
# Por fim, com o comando ''learn'' é possível criar novos comandos no ''kturtle''. Por exemplo, para criar um comando que desenhe um triângulo: <syntaxhighlight lang=text>
 
learn triangulo $lado {
 
repeat 3 {
 
  forward $lado
 
  turnleft 120
 
}
 
}
 
</syntaxhighlight>
 
Esse novo comando desenha um triângulo equilátero cujos lados tem comprimento dado pelo parâmetro ''$lado''. Ele poderia ser usado assim em um algoritmo: <syntaxhighlight lang=text>
 
learn triangulo $lado {
 
repeat 3 {
 
  forward $lado
 
  turnleft 120
 
}
 
}
 
triangulo 50
 
triangulo 100
 
triangulo 100
 
</syntaxhighlight>
 
Nesse exemplo, três triângulos são desenhados: um com lado 50, outro com lado 100, e um terceiro com lado 150. Veja que o número escrito logo após o comando ''triangulo'' irá aparecer no lugar de ''$lado'' no algoritmo que desenha o triângulo.
 
  
== 24/03:  Algoritmos ==
 
  
Sobre a [[SOP-2010-2-sobral#Exerc.C3.ADcios:_desenho_de_figuras_geom.C3.A9tricas|atividade da aula passada]]:
+
[[imagem:Scratch-var1.png]]
* [http://www.sj.ifsc.edu.br/~msobral/SOP/exemplos/kturtle/ Algoritmos dos fractais no Kturtle]
 
----
 
Os algoritmos que iremos criar serão compostos de:
 
* ''Estruturas de controle:'' estruturas para controlar a sequência de execução (realização) de algoritmos:
 
** ''Decisão:'' para realizar testes de forma a decidir que sequências de instruções devem ser executadas
 
** ''Repetição:'' para repetir sequências de instruções
 
* ''Estruturas de dados:'' estruturas para representar os dados a serem  processados por algoritmos
 
** ''Variáveis e constantes''
 
  
=== Portugol ===
 
  
As aulas de Lógica de Programação usarão um software de auxílio ao ensino de algoritmos chamado [http://orion.ipt.pt/%7Emanso/Portugol/ Portugol], desenvolvido na [http://www.dei.estt.ipt.pt/portal/ Escola Superior de Engenharia do Instituto Politécnico de Tomar], em Portugal.  
+
Variáveis podem ser ''globais'' ou ''locais'':
* [http://www.sj.ifsc.edu.br/~msobral/SOP/portugol.html Guia rápido de instalação e utilização do Portugol].
+
* ''Globais:'' são visíveis e podem ser usadas por qualquer objeto do Scratch.
 +
* ''Locais:'' são visíveis e podem ser usadas somente pelo objeto do Scratch ao qual está vinculada.
  
==== Guia rápido de instalação e utilização do Portugol ====
+
Variáveis podem ser usadas em qualquer comando que precise de um valor numérico, como por exemplo o comando para mover um certo número de passos. No exemplo abaixo, um programa faz com que um objeto desenhe um triângulo no palco, sendo que o comprimento do lado do triângulo é informado pelo usuário.
  
Abaixo segue uma breve ajuda de como obtê-lo, instalá-lo e usá-lo. Esse guia assume que você esteja usando o Ubuntu Linux 9.04 ou superior.
+
[[imagem:Scratch-var2.png]]
 +
 
 +
 
 +
Variáveis podem ser usadas em ''expressões aritméticas'', que realizam algum cálculo com valores numéricos. No Scratch expressões são criadas combinando-se os blocos contidos em ''Operadores''(blocos verdes-claros):
  
# Faça o [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/soft/portugol23.tar.gz download] do Portugol.
 
# Descompacte-o com o seguinte comando: <syntaxhighlight lang=bash>
 
tar xzf portugol23.tar.gz
 
</syntaxhighlight>
 
# Repare que existe agora um subdiretório portugol no diretório onde você o descompactou. Execute o Portugol com o seguinte comando: <syntaxhighlight lang=bash>
 
java -jar portugol/Portugol.jar
 
</syntaxhighlight> Obs: você precisará ter Java instalado. Caso não o tenha, execute o comando: <syntaxhighlight lang=bash>
 
sudo apt-get install openjdk-6-jre
 
</syntaxhighlight>
 
# Copie esse [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/exemplos/fluxogramas.cfg arquivo] para poder ver fluxogramas coloridos, e grave-o no memso diretório onde está o Portugol.
 
# Veja a [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/soft/help/index.html ajuda] do Portugol, e use-a sempre que tiver dúvidas !
 
  
<br>A tela inicial do Portugol segue abaixo, junto com um programa demonstrativo.<br>
+
[[imagem:Scratch-operadores1.png]]
  
[[Imagem:Editor-Portugol.png]]
 
  
Exemplos de programas iniciais em Portugol:
+
Usando esses blocos podem-se calcular novos valores usando variáveis ou constantes. Por exemplo, um pequeno programa que desenha um polígono qualquer precisa calcular o ângulo de quina da figura dependendo de sua quantidade de lados:
  
# ''Lendo um número e mostrando-o na tela em seguida:'' <syntaxhighlight lang=text>
 
Inicio
 
  inteiro x
 
  
  Escrever "Digite um numero: ",
+
[[imagem:Scratch-operadores2.png]]
  Ler X
 
  Escrever "Numero digitado: ", x
 
Fim
 
</syntaxhighlight>
 
# ''Lendo dois números, somando-os e mostrando o resultado na tela:'' <syntaxhighlight lang=text>
 
Inicio
 
  inteiro x, y
 
  
  Escrever "Digite um numero: ",
 
  Ler x
 
  Escrever "Digite outro numero: ",
 
  Ler y
 
  Escrever "Soma = ", x+y
 
Fim
 
</syntaxhighlight>O programa abaixo é equivalente:<syntaxhighlight lang=text>
 
Inicio
 
  inteiro x, y, z
 
  
  Escrever "Digite um numero: ",
+
Usando esses conceitos sobre variáveis e expressões, faça as atividades a seguir.
  Ler x
+
 
  Escrever "Digite outro numero: ",
+
=== Pong ===
  Ler y
+
 
  z <- x + y
+
Outro jogo clássico chamado [http://pt.wikipedia.org/wiki/Pong Pong] mostrava uma bola que refletia em uma parede, voltando e devendo ser interceptada por uma pequena base (que funcionava como raquete) comandada pelo jogador. Se conseguir interceptá-la, a bola é refletida de novo em direção à parede oposta, continuando assim o jogo. Se falhar, o jogo termina. Esse é considerado o primeiro videogame lucrativo a ter sido criado ...
  Escrever "Soma = ", z
 
Fim
 
</syntaxhighlight>
 
  
=== Atividades ===
+
[[imagem:Pong1.jpg]]
  
# ''Média de três números:'' escreva um programa para calcular a média de três números.
 
# ''Média balanceada de três números:'' escreva um programa para calcular a média balanceada de três números.
 
# ''Sequência de Fibonacci:'' em matemática corresponde aos números: <syntaxhighlight lang=text>
 
1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, ...
 
</syntaxhighlight>... que pode ser descrita pela relação de recorrência <br><br><math>F_{n} = F_{n-1} + F_{n-2}</math><br><br>... com valores iniciais <math>F_{0} = 1</math> e <math>F_{1} = 1</math>.<br><br>Numerosas formas na natureza apresentam essa sequência, como neste girassol (cujas flores se dispõem em uma espiral):<br><br>[[Imagem:Sunflower.jpg]]  [[Imagem:espiral_fibonacci.png]] [[Imagem:FibonacciBlocks.png]]<br><br>Usando o Portugol escreva um programa que mostre os 10 primeiros números dessa sequência.
 
# ''Distância até o horizonte:'' escreva um programa que calcule a distância dos seus olhos até o horizonte. Assuma que a Terra é perfeitamente esférica, e que seu raio tem 6.378 km. Considere que você esteja no nível do mar (seus pés tocando a água do mar ;-), e que o horizonte esteja num mar perfeitamente liso. ''Dica: faça um diagrama desse problema para visualizar sua geometria, e use trigonometria para resolvê-lo.
 
  
== 30/03: Algoritmos ==
+
Tente fazer uma versão do Pong usando o Scratch, mas com duas pequenas modificações. Há apenas uma base, que fica no canto inferior do palco. O placar conta quantas vezes a bola tocou o chão (i.e. o jogador falhou em interceptá-la), e se chegar a 0 o jogo termina. A segunda modificação é uma aceleração gradual da bola, que deve deve aumentar de velocidade a cada 5 segundos de jogo.
  
* Diagrama de blocos (fluxograma)
 
* Variáveis e constantes
 
  
=== Fluxogramas ===
+
Para que serão necessárias variáveis nesse jogo ?
  
Diagramas de bloco para auxiliar a descrição de algoritmos. Ajudam na compreensão do algoritmo, por poder visualizar o fluxo de execução.
+
==== O problema da reflexão da bola na barra ====
  
 +
Em aula vimos que para fazer a reflexão da bola com a barra deve-se calcular o ângulo de reflexão. No caso da barra estar na horizontal, esse ângulo deve ser calculado assim:
  
[[imagem:Fluxograma-soma.png]] Fluxograma para o algoritmo da média de trẽs números.
+
<math>NovaDirecao = 180^0 - Direcao</math>
  
<br>
+
No Scratch isso deve ser feito combinando-se o comando "Aponte para direção" e uma expressão para calcular a nova  direção. A direção atual do objeto está contida em sua variável local ''direção'' (predefinida nos comandos de ''Movimentos''):
  
'''Blocos de uso mais comum'''<br>
 
{| border="1" cellpadding="2"
 
!Bloco
 
!Descrição
 
!Exemplo
 
|-
 
|[[Imagem:Inicio.png]]||Inicio do fluxograma||
 
|-
 
|[[Imagem:Processamento.png]]||Processamento||
 
|-
 
|[[Imagem:Entrada.png]]||Entrada de dados (ler do teclado)||
 
|-
 
|[[Imagem:Saida.png]]||Saída de dados (mostrar na tela)||
 
|-
 
|[[Imagem:Decisao.png]]||Decisão (testar uma condição e bifurcar)||[[imagem:Ex-decisao.png]]
 
|-
 
|[[Imagem:Conector.png]]||Conector (juntar dos ou mais ramos do fluxograma)||[[imagem:Ex-conector.png]]
 
|-
 
|[[Imagem:Fim.png]]||Fim||
 
|}
 
  
Obs: [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/exemplos/fluxogramas.cfg Arquivo de configuração das cores do fluxograma ] do Portugol.
+
[[imagem:Scratch-reflexao.png]]
 +
 
 +
 
 +
==== Uma outra versão do Pong ====
 +
 
 +
Em uma outra versão ainda encontrada, no canto superior há um conjunto de alvos que devem ser acertados pela bola. Quando se acertarem todos os alvos o jogo termina.
 +
 
  
=== Variáveis e constantes ===
+
[[imagem:Pong2.jpg]]
  
* '''Variável:''' capaz de guardar um dado a ser usado no algoritmo. Pode ser entendida como uma caixa, onde se coloca um dado e se pode consultá-lo quantas vezes for necessário. O dado pode ser modificado (substituído por outro). Exemplo em Portugol: <syntaxhighlight lang=text>
+
=== Para casa: um jogo de sinuca ===
Inicio
 
  inteiro anos, dias
 
  
  Escrever "Quantos anos se passaram ? "
+
Para exercitar o uso de variáveis vamos criar também um jogo de sinuca. Nesse jogo deve-se usar a bola branca para encaçapar uma outra bola colorida. As bolas se movimentam de forma natural, desacelerando gradualmente devido ao atrito com a mesa. Quando as bolas colidem, suas velocidades e direções se modificam, dependendo de seus valores anteriores e do ângulo de colisão. Quando as bolas batem nos cantos das mesas, devem ser refletidas. Como as bolas predem velocidade gradualmente, dependendo de suas velocidades iniciais e das colisões em algum momento irão fatalmente parar. As caçapas ficam nos dois cantos superiores do palco. Você notará que sem o uso de variáveis, não será possível criar esse jogo, ainda mais se quiser acrescentar mais alguns detalhes.
  Ler anos
+
 
  dias <- anos * 365
+
As tacadas se fazem com um taco representado por uma linha reta, cuja ponta sempre está colada à bola branca. A direção do taco pode ser controlada pelo mouse ou por teclas direita e esquerda. Para fazer uma tacada, deve-se pressionar a tecla seta pra baixo durante um tempo, e então soltá-la. Quanto mais tempo se pressionar essa tecla mais forte será a tacada, e assim mais veloz a bola branca vai disparar. Assim, para realizar tacadas com pouca velocidade deve-se pressionar a tecla seta pra baixo por pouco tempo, e para tacadas mais fortes, em que a bola branca dispara com grande velocidade, deve-se pressionar essa tecla por um tempo maior. Pode-se usar algum objeto e colocá-lo na lateral do palco para informar qual a potência da tacada a ser realizada.
  Escrever "... então se passaram ", dias, " dias"
+
 
Fim
+
Alguns dados serão necessários para calcular as movimentações das bolas:
</syntaxhighlight> Nesse exemplo há duas variáveis: ''dias'' e ''anos''
+
* Peso de cada bola: 100 g
* '''Constante:''' semelhante à variável, porém o dado armazenado não pode ser modificado. Exemplo em Portugol:<syntaxhighlight lang=text>
+
* Diâmetro das bolas: 8 cm
Inicio
+
* Desaceleração das bolas devido ao atrito com a mesa: <math>0.1 ~m/s^2</math>
  constante inteiro diasPorAno <- 365
+
* Velocidade mínima de tacada: 0 m/s
  inteiro anos, dias
+
* Velocidade máxima de tacada: 4 m/s
 +
 
 +
== 30/03: Algoritmos: Usando variáveis, expressões e estruturas de decisão ==
 +
 
 +
'''Estruturas de decisão:''' blocos de controle usados quando devem-se executar comandos somente se uma determinada condição for verdadeira. Por exemplo, no jogo Pong a bola deve ser refletida se tocar na barra controlada pelo jogador:
  
  Escrever "Quantos anos se passaram ? "
+
[[imagem:Prg-se3.png]]
  Ler anos
 
  dias <- anos * diasPorAno
 
  Escrever "... então se passaram ", dias, " dias"
 
Fim
 
</syntaxhighlight> Nesse exemplo há uma constante: ''diasPorAno''
 
  
<br>
+
Esse tipo de estrutura de decisão se chama ''Se condição então faça algo''. Como indica sua descrição, uma ou mais instruções serão executadas caso a condição seja verdadeira. No exemplo acima, a condição é ''tocando em barra'', e as instruções executados caso isso seja verdade são ''aponte para a direção 180-direção''.
Variáveis e constantes devem ser declaradas antes de serem usadas (algumas poucas linguagens, como [http://www.python.org Python] e [http://www.perl.org Perl], não exigem isto). A declaração consiste do tipo e identificador da variável. O tipo corresponde ao tipo de valor que pode ser guardado, e o identificador é o nome da variável. No exemplo abaixo:
 
  
<syntaxhighlight lang=text>
 
  constante inteiro diasPorAno <- 365
 
  inteiro anos, dias
 
Fim
 
</syntaxhighlight>
 
  
No exemplo acima, há duas variáveis do tipo ''inteiro'', e seus identificadores são ''dias'' e ''anos''. O tipo ''inteiro'' indica que essas variáveis podem guardar somente números inteiros.
+
No exemplo do tiro ao helicóptero, inspirado no jogo Space invaders, o jogo deveria terminar quando o tiro acertasse o alvo. Assim, as instruções para término do jogo precisavam estar dentro de uma estrutura ''Se condição então ...'', como mostrado abaixo:
  
'''''Tipos de variáveis e constantes no Portugol:'''''
 
  
{| border="1" cellpadding="2"
+
[[imagem:Prg-se1.png]]
!Tipo
+
 
!Descrição
 
!Exemplo
 
|-
 
|Inteiro||Número inteiro entre -2 147 483 648 e 2 147 483 647 || Inteiro x <- 10
 
|-
 
|Real||Número real entre -1.7 E 308 e 1.7 E 308 || Real y <- 10.789
 
|-
 
|Lógico||Valor booleano, com valores "Verdadeiro" e "Falso" || Logico ok <- Falso
 
|-
 
|Caracter||Um caractere da [http://pt.wikipedia.org/wiki/ASCII tabela ASCII] || Caracter letra <- "A"
 
|-
 
|Texto||Uma sequência de caracteres (ou ''string'') || Texto palavra <- "um teste"
 
|}
 
  
A declaração de constantes é semelhante à de variáveis, bastanto prefixá-las com a palavra-chave ''constante''.
+
Para ilustrar o uso de ''Se condição então ...'', e o teste de condições em geral, hoje serão feitos dois projetos:
  
=== Expressões aritméticas ===
+
# A continuação do jogo Pong, em que a bola deve acertar alvos no topo da tela. Além disso, se a bola tocar no chão mais que 3 vezes o jogador perde.
 +
#* [http://tele.sj.ifsc.edu.br/~msobral/prg/pong0.sb Uma versão inicial do jogo Pong]
 +
# Um cronômetro a ser visualizado no palco.
  
Um conjunto de operações sobre variáveis, constantes e funções numéricas, e que gera um determinado resultado numérico.
+
== 31/03:  Algoritmos: ainda estruturas de decisão e também de repetição ==
  
Exemplos de expressões aritméticas: <syntaxhighlight lang=text>
+
Por diversas vezes criaram-se programas no Scratch em que o comportamento de um objeto corresponde a repetir uma sequência de comandos. Por exemplo, cada alvo no topo da tela no jogo Pong deve sumir quando for tocado pela bola:
# Uma expressão que calcula quantos segundos existem em um horário do tipo horas, minutos e segundos
 
3600*horas + 60*minutos + segundos
 
  
# Uma expressão que calcula a velocidade instantânea, segundo um MRV
+
[[imagem:Prg-repeticao1.gif]]
vel_inicial + aceleracao*tempo;
 
  
# Uma expressão que calcula o módulo de um vetor bidimensional, que possui coordenadas x e y
+
Assim, ele deve sempre testar se a bola o está tocando, e quando isso acontecer ele deve desaparecer e contabilizar que há uma alvo a menos para ser acertado. Como esse teste deve ser feito repetidamente até que a bola o acerte, torna-se necessário usar uma estrutura de repetição. No caso do Scratch, usou-se o comando ''Sempre'', que faz com que todos os comandos nele contidos sejam executados indefinidamente (no caso, até que a bola toque o alvo). Além dessa parte do programa, o teste se todos os alvos foram acertados também implica a repetição de uma sequência de comandos.
raiz(x^2 + y^2)  
 
</syntaxhighlight>
 
  
Os resultados de expressões podem ser mostrados na tela, ou armazenados em variáveis:
+
No jogo, a bola deve se movimentar pelo palco, refletindo nas paredes e sendo rebatida pela barra até que todos os alvos tenham sido acertados.
 +
Portanto, os comandos que implicam controlar seu movimento devem se repetir seguidamente até que essa condição de término seja alcançada. O comportamento da bola pode desta forma ser descrito simplificadamente pelos comandos mostrados abaixo, em que se usa a variável ''bananas'' para indicar quantos alvos faltam para serem acertados. A repetição foi obtida com o comando ''repita até bananas=0'', e dessa forma a repetição se interrompe quando a variável ''bananas'' tiver o valor 0.
  
<syntaxhighlight lang=text>
+
[[imagem:Prg-repeticao2.gif]]
# Uma expressão que calcula quantos segundos existem em um horário do tipo horas, minutos e segundos
 
segundos <- 3600*horas + 60*minutos + segundos
 
  
# Uma expressão que calcula a velocidade instantânea, segundo um MRV
+
Um terceiro exemplo diz respeito à criação de um cronômetro. Uma variável pode ser decrementada uma vez por segundo, até que o cronômetro zere. Um exemplo de como fazer isso segue abaixo:
escrever 'Velocidade no instante ', tempo, ' = ', vel_inicial + aceleracao*tempo;
 
  
# Uma expressão que calcula o módulo de um vetor bidimensional, que possui coordenadas x e y
+
[[imagem:Prg-repeticao4.png]]
modulo <- raiz(x^2 + y^2)
 
</syntaxhighlight>
 
  
Repare que uma expressão fica sempre do lado direito, quando atribuída a uma variável. A expressão é primeiro calculada, e em seguida seu resultado é armazenado na variável:
 
  
<syntaxhighlight lang=text>
+
Como se vê, estruturas de repetição são muito úteis para repetir sequências de comandos. Existem estruturas de repetição incondicionais, que repetem indefinidamente (como o comando ''sempre'' do Scratch), e condicionais, que repetem enquanto determinada condição for verdadeira ou até que determinada condição se verifique (ex: comando ''repita até''). Com elas se evita que programas sejam desnecessariamente longos ... na verdade sem elas seriam inviáveis muitos tipos de programas !
segundos <- 3600*horas + 60*minutos + segundos
 
</syntaxhighlight>
 
  
==== Operadores aritméticos ====
+
=== Atividade ===
  
Expressões aritméticas sao compostas por números e operadores aritméticos:
+
# Adicione o cronômetro na tela do seu jogo Pong. O cronômetro deve ser composto de dois dígitos.
 +
# O Pong poderia ficar mais difícil se os alvos fossem móveis e fugissem da bola. Assim, quando sentisse a bola se aproximando um alvo poderia acelerar ou reduzir sua velocidade, visando evitar uma colisão. Modifique então o Pong para que os alvos movam na horizontal de uma lado para o outro, e evitem a colisão com a bola.
  
Obs: para os exemplos abaixo são usadas estas variáveis: <syntaxhighlight lang=text>
+
== 06/04: Portugol ==
Real x, area, lado
 
inteiro dias, horas
 
</syntaxhighlight>
 
  
{| border="1" cellpadding="2"
+
'''Trabalho:''' deve-se entregar o jogo Pong com o cronômetro, conforme especificado na [[PRG-2011-1-sobral#Atividade|última aula sobre Scratch]].
!Operador
 
!Descrição
 
!Exemplo
 
|-
 
|<nowiki>+</nowiki>||Adição|| x <- x + 1
 
|-
 
|<nowiki>-</nowiki>||Subtração|| x <- x - 1
 
|-
 
|*||Multiplicação|| x <- x*x*x
 
|-
 
|/||Divisão|| dias <- horas / 24
 
|-
 
|%||Módulo (resto de divisão)|| horas <- horas % 24
 
|-
 
|^||Potenciação|| area <- lado^2
 
|}
 
  
Precedência dos operadores (nesta ordem): ^, *, /, %, + e -
+
'''Prazo de entrega:'' ''14/04/2011''
 +
 
 +
----
 +
Os algoritmos que iremos criar serão compostos de:
 +
* ''Estruturas de controle:'' estruturas para controlar a sequência de execução (realização) de algoritmos:
 +
** ''Decisão:'' para realizar testes de forma a decidir que sequências de instruções devem ser executadas
 +
** ''Repetição:'' para repetir sequências de instruções
 +
* ''Estruturas de dados:'' estruturas para representar os dados a serem  processados por algoritmos
 +
** ''Variáveis e constantes''
 +
 
 +
=== Portugol ===
  
A precedência pode ser modificada com o uso de parênteses. Ex:
+
As aulas de Lógica de Programação usarão um software de auxílio ao ensino de algoritmos chamado [http://orion.ipt.pt/%7Emanso/Portugol/ Portugol], desenvolvido na [http://www.dei.estt.ipt.pt/portal/ Escola Superior de Engenharia do Instituto Politécnico de Tomar], em Portugal.
 +
* [http://www.sj.ifsc.edu.br/~msobral/SOP/portugol.html Guia rápido de instalação e utilização do Portugol].
  
<syntaxhighlight lang=text>
+
==== Guia rápido de instalação e utilização do Portugol ====
escrever 1 + 2 * 3
 
escrever (1 + 2)*3
 
</syntaxhighlight>
 
  
No Portugol, existem também algumas [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/soft/help/funcoes_biblioteca.html funções úteis], como a função '''''raiz''''': <syntaxhighlight lang=text>
+
Abaixo segue uma breve ajuda de como obtê-lo, instalá-lo e usá-lo. Esse guia assume que você esteja usando o Ubuntu Linux 9.04 ou superior.
r <- raiz(x^2 + y^2)
 
</syntaxhighlight>
 
  
O resultado de expressões aritméticas depende dos tipos numéricos das variáveis e constantes: <syntaxhighlight lang=text>
+
# Faça o [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/soft/portugol23.tar.gz download] do Portugol.
inicio
+
# Descompacte-o com o seguinte comando: <syntaxhighlight lang=bash>
  real x
+
tar xzf portugol23.tar.gz
  inteiro y
+
</syntaxhighlight>
  inteiro resultadoInteiro
+
# Repare que existe agora um subdiretório portugol no diretório onde você o descompactou. Execute o Portugol com o seguinte comando: <syntaxhighlight lang=bash>
  real resultadoReal
+
java -jar portugol/Portugol.jar
 
+
</syntaxhighlight> Obs: você precisará ter Java instalado. Caso não o tenha, execute o comando: <syntaxhighlight lang=bash>
  x <- 9
+
sudo apt-get install openjdk-6-jre
  y <- 9
+
</syntaxhighlight>
 
+
# Copie esse [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/exemplos/fluxogramas.cfg arquivo] para poder ver fluxogramas coloridos, e grave-o no memso diretório onde está o Portugol.
  escrever "O resultado de uma expressão aritmética depende dos tipos das variáveis e constantes\n"
+
# Veja a [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/soft/help/index.html ajuda] do Portugol, e use-a sempre que tiver dúvidas !
  escrever "usadas na expressão. Se forem todas inteiras, então o resultado será inteiro.\n"
 
  escrever "Veja este exemplo: \n"
 
  escrever "Variável inteira y=", y
 
  escrever "\nExpressão: y/2=", y/2
 
 
 
  escrever "\n\nNeste segundo exemplo, repete-se a mesma expressão, porém usando-se uma\n"
 
  escrever "variável real:\n"
 
  escrever "Variável real x=", x
 
  escrever "\nExpressão: x/2=", x/2
 
 
 
  x <- 4
 
  y <- 5
 
  escrever "\n\nSe as variáveis de diferentes tipos forem combinadas, o resultado da\n"
 
  escrever "expressão será real:\n"
 
  escrever "Variável real x=", x, " e inteira y=", y
 
  escrever "\nExpressão: (x+y)/2=", (x+y)/2
 
  
  escrever "\n\nNo entanto, se uma expressão tiver um resultado real, mas este for\n"
+
<br>A tela inicial do Portugol segue abaixo, junto com um programa demonstrativo.<br>
  escrever "atribuído a uma variável inteira, então apenas a parte inteira será guardada:\n"
 
  escrever "Variável real x=", x, " e inteira y=", y
 
  y <- (x+y)/2
 
  escrever "\nExpressão: y <- (x+y)/2 ... após executada, y=", y
 
 
 
fim
 
</syntaxhighlight>
 
  
=== Atividade ===
+
[[Imagem:Editor-Portugol.png]]
  
Para os exercícios abaixo, desenhe o fluxograma e escreva o algoritmo no Portugol.
+
Exemplos de programas iniciais em Portugol:
  
# Faça um algoritmo que, usando somente duas variáveis, calcule a média de quatro números.
+
# ''Lendo um número e mostrando-o na tela em seguida:'' <syntaxhighlight lang=text>
# Escreva um algoritmo que calcule as raizes de uma equação de 2o grau.
+
Inicio
# Um equipamento conta o tempo desde que foi ligado. No entanto, essa contagem é feita em segundos. Faça um algoritmo que converta o valor desse contador para horas, minutos e segundos. Ex: se o contador tiver o valor 43397, o seu programa deve mostrar: 12:03:17.
+
  inteiro x
# Crie um conversor de decimal para binário (limite: 4 bits). Ex.: tendo o número 10 (decimal) de entrada, deve-se obter o número 1010 (binário) de saída.
 
# Escreva um algoritmo que leia o nome, sobrenome e idade de uma pessoa, e escreva na tela (no lugar dos colchetes devem aparecer os valores lidos):<syntaxhighlight lang=text>
 
Nome: [sobrenome, nome]
 
Idade: [idade] anos</syntaxhighlight>
 
# Crie um gerador automático de código Logo para desenhar polígonos:
 
#* Ler um número do usuário.
 
#* Calcular o ângulo interno.
 
#* Apresentar como resultado o código [http://pt.wikipedia.org/wiki/Logo Logo]  a ser inserido no programa '''kturtle'''. Ex.: se o usuário digitar o número 3, o código será de um triângulo equilátero, cuja soma dos ângulos internos é 180 - logo, cada ângulo será de 60 graus (no Logo, lembre-se que o ângulo a ser usado é o complemento de 180, conforme visto em aula). Se o usuário digitar 5 ao invés de 3, teremos um pentágono. Abaixo temos soluções para triângulo e pentágono:
 
reset
 
repeat 3
 
{
 
  forward 100
 
  turnright 120
 
}
 
  
reset
+
  Escrever "Digite um numero: ",
repeat 5
+
  Ler X
{
+
  Escrever "Numero digitado: ", x
  forward 100
+
Fim
  turnright 72
+
</syntaxhighlight>
}
+
# ''Lendo dois números, somando-os e mostrando o resultado na tela:'' <syntaxhighlight lang=text>
 +
Inicio
 +
  inteiro x, y
  
 +
  Escrever "Digite um numero: ",
 +
  Ler x
 +
  Escrever "Digite outro numero: ",
 +
  Ler y
 +
  Escrever "Soma = ", x+y
 +
Fim
 +
</syntaxhighlight>O programa abaixo é equivalente:<syntaxhighlight lang=text>
 +
Inicio
 +
  inteiro x, y, z
  
 +
  Escrever "Digite um numero: ",
 +
  Ler x
 +
  Escrever "Digite outro numero: ",
 +
  Ler y
 +
  z <- x + y
 +
  Escrever "Soma = ", z
 +
Fim
 +
</syntaxhighlight>
  
== 31/03: Estruturas de decisão ==
+
=== Atividades ===
 
 
O exemplo abaixo está contido no livro ''Classification and Regression Trees'', de Leo Breiman, Jerome Friedman, Richard Olshen e Charles Stone, editora Chapman & Hall, 1984.
 
 
 
Na Universidade da California, no centro Médico de San Diego, quando um paciente com ataque cardíaco é recebido, dezenove variáveis são medidas ao longo das primeiras 24 horas. Essas incluem pressão sanguínea, idade, e 17 outras variáveis ordenadas e binárias (booleanas) que sumarizam os sintomas médicos considerados importantes indicadores da condição do paciente.
 
  
O objetivo  de um estudo médico feito entre os anos 70 e 80 foi o desenvolvimento de um método para identificar pacientes de alto risco (que não sobreviverão ao menos 30 dias) com base nos dados obtidos nas primeiras 24 horas. O diagrama abaixo mostra uma regra de classificação que foi produzida nesse estudo. A letra F significa que não há um risco alto, e a letra G quer dizer paciente de alto risco.
+
# ''Média de três números:'' escreva um programa para calcular a média de três números.
 +
# ''Média balanceada de três números:'' escreva um programa para calcular a média balanceada de três números.
 +
# ''Sequência de Fibonacci:'' em matemática corresponde aos números: <syntaxhighlight lang=text>
 +
1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, ...
 +
</syntaxhighlight>... que pode ser descrita pela relação de recorrência <br><br><math>F_{n} = F_{n-1} + F_{n-2}</math><br><br>... com valores iniciais <math>F_{0} = 1</math> e <math>F_{1} = 1</math>.<br><br>Numerosas formas na natureza apresentam essa sequência, como neste girassol (cujas flores se dispõem em uma espiral):<br><br>[[Imagem:Sunflower.jpg]] [[Imagem:espiral_fibonacci.png]] [[Imagem:FibonacciBlocks.png]]<br><br>Usando o Portugol escreva um programa que mostre os 10 primeiros números dessa sequência.
 +
# ''Distância até o horizonte:'' escreva um programa que calcule a distância dos seus olhos até o horizonte. Assuma que a Terra é perfeitamente esférica, e que seu raio tem 6.378 km. Considere que você esteja no nível do mar (seus pés tocando a água do mar ;-), e que o horizonte esteja num mar perfeitamente liso. ''Dica: faça um diagrama desse problema para visualizar sua geometria, e use trigonometria para resolvê-lo.
  
[[imagem:Crt-decisao.png]]
+
== 13/04: Algoritmos ==
  
Essa regra classifica os pacientes como F ou G dependendo de respostas do tipo sim/não a no máximo três perguntas. Como  seria um algoritmo que a implementasse ?
+
=== Variáveis e constantes ===
  
----
+
* '''Variável:''' capaz de guardar um dado a ser usado no algoritmo. Pode ser entendida como uma caixa, onde se coloca um dado e se pode consultá-lo quantas vezes for necessário. O dado pode ser modificado (substituído por outro). Exemplo em Portugol: <syntaxhighlight lang=text>
 +
Inicio
 +
  inteiro anos, dias
  
Algoritmos para resolver problemas como  o exemplo acima dependem de se poder expressar a '''''tomada de decisões'''''. Deve ser possível testar '''''condições''''', como  por exemplo "''a idade é maior que 62.5 anos ?''", e executar instruções dependendo do resultado do teste. Em Lógica de Programação, e em linguagens de programação em geral, isso se faz com '''''estruturas de decisão'''''.
+
  Escrever "Quantos anos se passaram ? "
 
+
  Ler anos
'''''Estruturas de decisão''''' possibilitam que se executem diferentes sequências de instruções de um programa, dependendo de uma condição a ser avaliada. Por exemplo, um jogo poderia armazenar a maior pontuação já obtida, e verificar se foi ultrapassada ao final de cada partida:
+
  dias <- anos * 365
 
+
  Escrever "... então se passaram ", dias, " dias"
<syntaxhighlight lang=text>
+
Fim
   Se pontuacao > recorde então
+
</syntaxhighlight> Nesse exemplo há duas variáveis: ''dias'' e ''anos''
    recorde <- pontuação
+
* '''Constante:''' semelhante à variável, porém o dado armazenado não pode ser modificado. Exemplo em Portugol:<syntaxhighlight lang=text>
   FimSe
+
Inicio
</syntaxhighlight>
+
   constante inteiro diasPorAno <- 365
 +
   inteiro anos, dias
  
O exemplo em Portugol acima mostra a estrutura de decisão ''Se condição entao comandos Fimse''. O equivalente em  fluxograma é:
+
  Escrever "Quantos anos se passaram ? "
 +
  Ler anos
 +
  dias <- anos * diasPorAno
 +
  Escrever "... então se passaram ", dias, " dias"
 +
Fim
 +
</syntaxhighlight> Nesse exemplo há uma constante: ''diasPorAno''
  
[[imagem:Seentao.png]]
+
<br>
 
+
Variáveis e constantes devem ser declaradas antes de serem usadas (algumas poucas linguagens, como [http://www.python.org Python] e [http://www.perl.org Perl], não exigem isto). A declaração consiste do tipo e identificador da variável. O tipo corresponde ao tipo de valor que pode ser guardado, e o identificador é o nome da variável. No exemplo abaixo:
Veja o próximo exemplo:
 
  
 
<syntaxhighlight lang=text>
 
<syntaxhighlight lang=text>
   Se conceito > 70 entao
+
   constante inteiro diasPorAno <- 365
    escrever 'Voce esta aprovado'
+
   inteiro anos, dias
   senao
+
Fim
    escrever 'Desta vez não deu ... tente de novo !'
 
  Fimse
 
 
</syntaxhighlight>
 
</syntaxhighlight>
  
O uso de ''Se condição entao comandos Senao comandos Fimse'' possibilita que se execute uma sequência de comandos se a condição for verdadeira, e outra sequência se for falsa. Seu equivalente em  fluxograma é:
+
No  exemplo acima, há duas variáveis do tipo ''inteiro'', e seus identificadores são ''dias'' e ''anos''. O tipo ''inteiro'' indica que essas variáveis podem guardar somente números inteiros.
  
[[imagem:Seentaosenao.png]]
+
'''''Tipos de variáveis e constantes no Portugol:'''''
 
 
Para fazer um bom uso de estruturas de decisão deve-se primeiro conseguir identificar as condições a serem avaliadas. Condições são escritas com expressões lógicas, e estas são compostas de operadores lógicos e relacionais aplicados a variáveis e constantes.
 
 
 
=== Condições ===
 
 
 
Condições representam os testes que precisam ser feitos com dados do problema. Esses testes são expressados por '''''expressões lógicas''''', cujos resultados são ''verdadeiro'' ou ''falso''. Expressões lógicas são construídas usando-se '''''operadores lógicos''''' e '''''operadores relacionais''''' para comparar e avaliar os valores de variáveis e constantes.
 
 
 
Obs: para os exemplos abaixo são usadas estas variáveis: <syntaxhighlight lang=text>
 
Logico correto, multa, aprovado, barato, bombear_agua
 
Logico descartar, baixo, reprovado, erro, enviado, recebido
 
inteiro erros, pontuacao, preco, endereco, velocidade
 
Real faltas, nivel_agua, altura
 
</syntaxhighlight>
 
 
 
==== Operadores relacionais ====
 
 
 
Operadores relacionais são usados para comparar valores, e estão listados  na tabela abaixo. Cada comparação feita com esses operadores forma uma ''expressão lógica simples''. Portanto, o resultado de uma comparação é um valor lógico que pode ser ''verdadeiro'' ou ''falso''.
 
  
 
{| border="1" cellpadding="2"
 
{| border="1" cellpadding="2"
  !Operador
+
  !Tipo
 
  !Descrição
 
  !Descrição
 
  !Exemplo
 
  !Exemplo
 
  |-
 
  |-
  |=||Igualdade|| correto <- (erros = 0)
+
  |Inteiro||Número inteiro entre -2 147 483 648 e 2 147 483 647 || Inteiro x <- 10
 
  |-
 
  |-
  |>||Maior|| multa <- (velocidade > 80)
+
  |Real||Número real entre -1.7 E 308 e 1.7 E 308 || Real y <- 10.789
 
  |-
 
  |-
  |>=||Maior ou igual|| aprovado <- (pontuacao >= 70)
+
  |Lógico||Valor booleano, com valores "Verdadeiro" e "Falso" || Logico ok <- Falso
 
  |-
 
  |-
  |<||Menor|| barato <- (preco < 100)
+
  |Caracter||Um caractere da [http://pt.wikipedia.org/wiki/ASCII tabela ASCII] || Caracter letra <- "A"
 
  |-
 
  |-
  |<=||Menor ou igual|| bombear_agua <- (nivel_agua <= 0.7)
+
  |Texto||Uma sequência de caracteres (ou ''string'') || Texto palavra <- "um teste"
|-
 
|=/=||Diferente|| descartar <- (endereco =/= 12345)
 
 
|}
 
|}
  
==== Operadores lógicos ====
+
A declaração de constantes é semelhante à de variáveis, bastanto prefixá-las com a palavra-chave ''constante''.
  
Operadores lógicos são usados para combinar expressões lógicas simples, criando assim ''expressões lógicas compostas'', e estão listados  na tabela abaixo.
+
=== Expressões aritméticas ===
  
{| border="1" cellpadding="2"
+
Um conjunto de operações sobre variáveis, constantes e funções numéricas, e que gera um determinado resultado numérico.
!Operador
 
!Descrição
 
!Exemplo
 
|-
 
|NAO||Negação|| baixo <- NAO (altura > 1.8)
 
|-
 
|E||Conjunção|| aprovado <- NAO (conceito = "D") E (faltas <= 0.25)
 
|-
 
|OU||Disjunção|| reprovado <- (conceito = "D") OU (faltas > 0.25)
 
|-
 
|XOU||Disjunção exclusiva|| erro <- enviado XOU recebido
 
|}
 
  
Precedência dos operadores (nesta ordem): NAO, E, OU e XOU
+
Exemplos de expressões aritméticas: <syntaxhighlight lang=text>
 +
# Uma expressão que calcula quantos segundos existem em um horário do tipo horas, minutos e segundos
 +
3600*horas + 60*minutos + segundos
  
Lembre que a precedência pode ser modificada com o uso de parênteses.
+
# Uma expressão que calcula a velocidade instantânea, segundo um MRV
 +
vel_inicial + aceleracao*tempo;
  
=== Atividades ===
+
# Uma expressão que calcula o módulo de um vetor bidimensional, que possui coordenadas x e y
 +
raiz(x^2 + y^2)
 +
</syntaxhighlight>
  
# Faça um programa que leia um número e então informe se ele é par ou ímpar.
+
Os resultados de expressões podem ser mostrados na tela, ou armazenados em variáveis:
# Um radar de trânsito faz a medição de velocidade de veículos e, dependendo do valor, calcula a multa a ser aplicada. Em uma determinada via esse radar foi configurado da seguinte forma:
 
#* Se a velocidade for maior que 80 km/h, a multa é de R$ 360.
 
#* Se a velocidade for maior que 60 km/h, a multa é de R$ 180.
 
#* Se a velocidade for menor ou igual a 60 km/h, não há multa.<br><br>Escreva um algoritmo que calcule a multa de acordo com a velocidade de um veículo.
 
# Faça um algoritmo que leia três números do teclado, e mostre o maior e menor números.
 
# Escreva um  algoritmo  que faça o [[SOP-2010-2-sobral#20.2F09:_Estruturas_de_decis.C3.A3o|teste de risco de paciente cardíaco]], mostrado no início da aula.
 
# Um estudo sobre sensibilidade de pessoas a temperaturas da água identificou que a maioria das pessoas considera fria a água com temperaturas abaixo de 25 graus, morna entre 25 e 30 graus, e quente acima de 30 graus. Escreva um algoritmo que mostre as palavras "fria", "morna" ou "quente" dependendo da temperatura da água que for informada.
 
# Em uma rede de computadores, o ''firewall'' restringe o acesso a Internet dependendo do horário e do tipo de usuário que faz o acesso. Os tipos de usuário abaixo têm as seguintes restrições:
 
#* Funcionario: apenas entre 0:00 e 7:30, entre 18:30 e 0:00, e entre 12:00 e 13:30
 
#* Financeiro: qualquer horario
 
#* Diretoria: qualquer horário<br>Escreva um algoritmo que informe se um acesso foi permitido, em função do horário e do tipo de usuário.
 
# Modifique o algoritmo acima para adicionar a seguinte restrição:
 
#* Funcionario: nao pode acessar sites de jornal (ex: www.rbs.com.br)
 
#* Financeiro: nao pode acessar sites de jornal durante o expediente
 
#* Diretoria: sem restrições a sites
 
# Faça um algoritmo para fazer a divisão de dois números reais. Antes de dividi-los deve ser feito um teste de validade. Caso não seja possível dividi-los, deve ser mostrada uma mensagem de erro. Se for possível, deve-se mostrar o resultado da divisão.
 
# Faça um jogo de par ou ímpar, em que o jogador aposta contra o computador. O jogador deve digitar um número entre 0 e 5 e optar entre par ou ímpar. O computador deve sortear um número também entre 0 e 5. Se a paridade da soma dos números do jogador e do computador for a mesma que o jogador optou, então ele ganha a partida, senão o computador vence.
 
# Escreva um algoritmo para identificar se há, dentre três palavras lidas do teclado, ao menos duas palavras distintas que pertençam ao conjunto {azul, preto, vermelho}. Exemplos:
 
#* Se o usuário digitar ''verde'', ''preto'', ''vermelho'', o programa deve mostrar na tela ''verdadeiro''
 
#* Se o usuário digitar ''verde'', ''preto'', ''preto'', o programa deve mostrar na tela ''falso''
 
#* Se o usuário digitar ''azul'', ''preto'', ''azul'', o programa deve mostrar na tela ''verdadeiro'' <br>''Solução vista em aula:''<syntaxhighlight lang=text>
 
// Neste algoritmo deve-se identificar se ao menos duas palavras
 
// diferentes têm os valores azul, preto ou vermelho.
 
// A variável inteira "cont" conta quantas palavras diferentes
 
// tem esses valores.
 
  
inicio
+
<syntaxhighlight lang=text>
    texto p1 , p2 , p3
+
# Uma expressão que calcula quantos segundos existem em um horário do tipo horas, minutos e segundos
    inteiro cont <- 0
+
segundos <- 3600*horas + 60*minutos + segundos
   
+
 
    escrever "Palavra 1: "
+
# Uma expressão que calcula a velocidade instantânea, segundo um MRV
    ler p1
+
escrever 'Velocidade no instante ', tempo, ' = ', vel_inicial + aceleracao*tempo;
    escrever "Palavra 2: "
 
    ler p2
 
    escrever "Palavra 3: "
 
    ler p3
 
   
 
    // ao menos uma palavra é "azul" ?
 
    se p1 = "azul" OU p2 = "azul" OU p3 = "azul" entao
 
      cont <- 1
 
    fimse
 
  
    // ao menos uma palavra é "preto" ?
+
# Uma expressão que calcula o módulo de um vetor bidimensional, que possui coordenadas x e y
    se p1 = "preto" OU p2 = "preto" OU p3 = "preto" entao
+
modulo <- raiz(x^2 + y^2)
      cont <- cont + 1
+
</syntaxhighlight>
    fimse
 
  
    // ao menos uma palavra é "vermelho" ?
+
Repare que uma expressão fica sempre do lado direito, quando atribuída a uma variável. A expressão é primeiro calculada, e em seguida seu resultado é armazenado na variável:
    se p1 = "vermelho" OU p2 = "vermelho" OU p3 = "vermelho" entao
 
      cont <- cont + 1
 
    fimse
 
  
    // se duas ou mais palavras diferentes têm aqueles valores,
+
<syntaxhighlight lang=text>
    // então mostra VERDADEIRO
+
segundos <- 3600*horas + 60*minutos + segundos
    se cont > 1 entao
 
      escrever "VERDADEIRO"
 
    senao
 
      escrever "FALSO"
 
    fimse
 
       
 
fim
 
 
</syntaxhighlight>
 
</syntaxhighlight>
  
== 21/09: estruturas de decisão ==
+
==== Operadores aritméticos ====
  
Há situações em que se precisa fazer um conjunto de comparações, como mostrado abaixo:
+
Expressões aritméticas sao compostas por números e operadores aritméticos:
  
<syntaxhighlight lang=text>
+
Obs: para os exemplos abaixo são usadas estas variáveis: <syntaxhighlight lang=text>
// Lê a data no formato numérico dia, mes, ano, e mostra a data no formato
+
Real x, area, lado
// dia, nome do mês, ano.
+
inteiro dias, horas
Inicio
+
</syntaxhighlight>
  inteiro dia, mes, ano
 
  texto nome_mes
 
  
  escrever "Dia: "
+
{| border="1" cellpadding="2"
  ler dia
+
!Operador
  escrever "Mes: "
+
!Descrição
  ler mes
+
!Exemplo
  escrever "Ano: "
+
|-
  ler ano
+
|<nowiki>+</nowiki>||Adição|| x <- x + 1
 +
|-
 +
|<nowiki>-</nowiki>||Subtração|| x <- x - 1
 +
|-
 +
|*||Multiplicação|| x <- x*x*x
 +
|-
 +
|/||Divisão|| dias <- horas / 24
 +
|-
 +
|%||Módulo (resto de divisão)|| horas <- horas % 24
 +
|-
 +
|^||Potenciação|| area <- lado^2
 +
|}
 +
 
 +
Precedência dos operadores (nesta ordem): ^, *, /, %, + e -
 +
 
 +
A precedência pode ser modificada com o uso de parênteses. Ex:
  
  se mes = 1 entao
+
<syntaxhighlight lang=text>
    nome_mes <- "Janeiro"
+
escrever 1 + 2 * 3
  senao
+
escrever (1 + 2)*3
    se mes = 2 entao
+
</syntaxhighlight>
      nome_mes <- "Fevereiro"
+
 
    senao
+
No Portugol, existem também algumas [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/soft/help/funcoes_biblioteca.html funções úteis], como a função '''''raiz''''': <syntaxhighlight lang=text>
      se mes = 3 entao
+
r <- raiz(x^2 + y^2)
        nome_mes <- "Março"
+
</syntaxhighlight>
      senao
+
 
        se mes = 4 entao
+
O resultado de expressões aritméticas depende dos tipos numéricos das variáveis e constantes: <syntaxhighlight lang=text>
          nome_mes <- "Abril"
+
inicio
        senao
+
  real x
          se mes = 5 entao
+
  inteiro y
            nome_mes <- "Maio"
+
  inteiro resultadoInteiro
          senao
+
  real resultadoReal
            se mes = 6 entao
+
              nome_mes <- "Junho"
+
  x <- 9
            senao
+
  y <- 9
              se mes = 7 entao
+
                nome_mes <- "Julho"
+
  escrever "O resultado de uma expressão aritmética depende dos tipos das variáveis e constantes\n"
              senao
+
  escrever "usadas na expressão. Se forem todas inteiras, então o resultado será inteiro.\n"
                se mes = 8 entao
+
  escrever "Veja este exemplo: \n"
                  nome_mes <- "Agosto"
+
  escrever "Variável inteira y=", y
              senao
+
  escrever "\nExpressão: y/2=", y/2
                  se mes = 9 entao
+
                    nome_mes <- "Setembro"
+
  escrever "\n\nNeste segundo exemplo, repete-se a mesma expressão, porém usando-se uma\n"
                  senao
+
  escrever "variável real:\n"
                    se mes = 10 entao
+
  escrever "Variável real x=", x
                      nome_mes <- "Outubro"
+
  escrever "\nExpressão: x/2=", x/2
                    senao
+
                      se mes = 11 entao
+
  x <- 4
                        nome_mes <- "Novembro"
+
  y <- 5
                      senao
+
  escrever "\n\nSe as variáveis de diferentes tipos forem combinadas, o resultado da\n"
                        nome_mes <- "Dezembro"
+
  escrever "expressão será real:\n"
                      fimSe
+
  escrever "Variável real x=", x, " e inteira y=", y
                    fimSe
+
  escrever "\nExpressão: (x+y)/2=", (x+y)/2
                  fimSe
+
                fimSe
+
  escrever "\n\nNo entanto, se uma expressão tiver um resultado real, mas este for\n"
              fimSe
+
  escrever "atribuído a uma variável inteira, então apenas a parte inteira será guardada:\n"
            fimSe
+
  escrever "Variável real x=", x, " e inteira y=", y
          fimSe
+
  y <- (x+y)/2
        fimSe
+
  escrever "\nExpressão: y <- (x+y)/2 ... após executada, y=", y
      fimSe
+
    fimSe
+
fim
   fimSe
+
 
 +
</syntaxhighlight>
 +
 
 +
=== Atividade ===
 +
 
 +
Para os exercícios abaixo, escreva o algoritmo no Portugol.
 +
 
 +
# Faça um algoritmo que, usando somente duas variáveis, calcule a média de quatro números.
 +
# Escreva um algoritmo que calcule as raizes de uma equação de 2o grau.
 +
# Um equipamento conta o tempo desde que foi ligado. No entanto, essa contagem é feita em segundos. Faça um algoritmo que converta o valor desse contador para horas, minutos e segundos. Ex: se o contador tiver o valor 43397, o seu programa deve mostrar: 12:03:17. <syntaxhighlight lang=text>
 +
inicio
 +
   inteiro h,m,s
  
   escrever dia, " de ", nome_mes, " de ", ano
+
   escrever "Quantos segundos mostrou o equipamento ? "
 +
  ler s
 +
 
 +
  h <- s /3600
 +
  s <- s % 3600  // s <- s - h*3600
 +
  m <- s /60
 +
  s <- s % 60 // s <- s - m*60
 +
 
 +
  escrever h, ":", m, ":", s
 +
 
 
fim
 
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Além de ser trabalhoso esse encadeamento de ''Se ... entao ... senao'', o algoritmo resultante fica pouco legível. Quer dizer, ele fica feio e difícil de entender.  
+
== 14/04: Variáveis e expressões ==
 +
 
 +
Continuação ...
  
Existe uma estrutura de decisão criada justamente para casos como esse, e que resulta em um algoritmo mais limpo e compreensível:
+
=== Exercícios ===
  
<syntaxhighlight lang=text>
+
# Crie um conversor de decimal para binário (limite: 4 bits). Ex.: tendo o número 10 (decimal) de entrada, deve-se obter o número 1010 (binário) de saída.
// Lê a data no formato numérico dia, mes, ano, e mostra a data no formato
+
# Escreva um algoritmo que leia o nome, sobrenome e idade de uma pessoa, e escreva na tela (no lugar dos colchetes devem aparecer os valores lidos):<syntaxhighlight lang=text>
// dia, nome do mês, ano.
+
Nome: [sobrenome, nome]
Inicio
+
Idade: [idade] anos</syntaxhighlight>
  inteiro dia, mes, ano
+
# A função exponencial <math>f(x) = e^x</math> pode ser calculada por uma série de Taylor:<br><math>f(x) \approx 1+x+\frac{x^2}{2}+\frac{x^3}{6}+...+\frac{x^n}{n!}</math><br> Faça um  algoritmo para calcular o valor desta função.
  texto nome_mes
+
 
 +
== 16/04: Estruturas de decisão ==
 +
 
 +
O exemplo abaixo está contido no livro ''Classification and Regression Trees'', de Leo Breiman, Jerome Friedman, Richard Olshen e Charles Stone, editora Chapman & Hall, 1984.
 +
 
 +
Na Universidade da California, no centro Médico de San Diego, quando um paciente com ataque cardíaco é recebido, dezenove variáveis são medidas ao longo das primeiras 24 horas. Essas incluem pressão sanguínea, idade, e 17 outras variáveis ordenadas e binárias (booleanas) que sumarizam os sintomas médicos considerados importantes indicadores da condição do paciente.
 +
 
 +
O objetivo  de um  estudo médico feito entre os anos 70 e 80 foi o desenvolvimento de um método para identificar pacientes de alto risco (que não sobreviverão ao menos 30 dias) com  base nos dados obtidos nas primeiras 24 horas. O diagrama abaixo mostra uma regra de classificação que foi produzida nesse estudo. A letra F  significa que não há um risco alto, e a letra G quer dizer paciente de alto risco.
  
  escrever "Dia: "
+
[[imagem:Crt-decisao.png]]
  ler dia
 
  escrever "Mes: "
 
  ler mes
 
  escrever "Ano: "
 
  ler ano
 
  
  Escolhe mes
+
Essa regra classifica os pacientes como F ou G dependendo de respostas do tipo sim/não a no máximo três perguntas. Como  seria um algoritmo que a implementasse ?
    caso 1:
 
      nome_mes <- "Janeiro"
 
    caso 2:
 
      nome_mes <- "Fevereiro"
 
    caso 3:
 
      nome_mes <- "Março"
 
    caso 4:
 
      nome_mes <- "Abril"
 
    caso 5:
 
      nome_mes <- "Maio"
 
    caso 6:
 
      nome_mes <- "Junho"
 
    caso 7:
 
      nome_mes <- "Julho"
 
    caso 8:
 
      nome_mes <- "Agosto"
 
    caso 9:
 
      nome_mes <- "Setembro"
 
    caso 10:
 
      nome_mes <- "Outubro"
 
    caso 11:
 
      nome_mes <- "Novembro"
 
    Defeito:
 
      nome_mes <- "Dezembro"
 
  fimEscolhe
 
  
  escrever dia, " de ", nome_mes, " de ", ano
+
----
fim
 
</syntaxhighlight>
 
 
 
A estrutura de decisão ''escolhe ... caso'' tem uma certa flexibilidade. No exemplo abaixo, mostra-se a possibilidade de testar mais de um valor no mesmo ''caso'':
 
  
<syntaxhighlight lang=text>
+
Algoritmos para resolver problemas como  o exemplo acima dependem de se poder expressar a '''''tomada de decisões'''''. Deve ser possível testar '''''condições''''', como  por exemplo "''a idade é maior que 62.5 anos ?''", e executar instruções dependendo do resultado do teste. Em Lógica de Programação, e em linguagens de programação em geral, isso se faz com '''''estruturas de decisão'''''.
inicio   
 
  caracter sexo   
 
  
  escrever "Qual o seu sexo (f/m):"   
+
'''''Estruturas de decisão''''' possibilitam que se executem diferentes sequências de instruções de um programa, dependendo de uma condição a ser avaliada. Por exemplo, um jogo poderia armazenar a maior pontuação já obtida, e verificar se foi ultrapassada ao final de cada partida:
  ler sexo   
 
  
   escrever "Olá "      
+
<syntaxhighlight lang=text>
 +
   Se pontuacao > recorde então
 +
     recorde <- pontuação
 +
  FimSe
 +
</syntaxhighlight>
 +
 
 +
O exemplo em Portugol acima mostra a estrutura de decisão ''Se condição entao comandos Fimse''. O equivalente em  fluxograma é:
 +
 
 +
[[imagem:Seentao.png]]
  
  escolhe sexo       
+
Veja o próximo exemplo:
    caso "m", "M" :            
 
      escrever "senhor"       
 
    caso "f","F" :           
 
      escrever "senhorita"       
 
    defeito :           
 
      escrever "Sexo indefinido"   
 
  fimescolhe   
 
  
   escrever ", benvindo ao portugol"
+
<syntaxhighlight lang=text>
fim
+
   Se conceito > 70 entao
 +
    escrever 'Voce esta aprovado'
 +
  senao
 +
    escrever 'Desta vez não deu ... tente de novo !'
 +
  Fimse
 
</syntaxhighlight>
 
</syntaxhighlight>
  
=== Atividades ===
+
O uso de ''Se condição entao comandos Senao comandos Fimse'' possibilita que se execute uma sequência de comandos se a condição for verdadeira, e outra sequência se for falsa. Seu equivalente em  fluxograma é:
  
# Faça um algoritmo que converta um número de 1 a 7 para o respectivo dia da semana (ex: 1 = domingo, 2 = 2a feira, e assim por diante).
+
[[imagem:Seentaosenao.png]]
# Faça uma calculadora com as quatro operações aritméticas. Sua calculadora deve ler (nesta ordem) o primeiro número, a operação aritmética (que deve ser informada usando o símbolo da respectiva operação: +, -, * ou /), e depois o segundo número. Ao final, seu algoritmo deve mostrar o resultado, ou uma mensagem de erro se a operação não for possível de realizar (ex: divisão por zero).
+
 
# A previsão do tempo na costa brasileira pode ser feita de forma aproximada usando-se um barômetro e um termômetro. Uma estimativa com boa chance de acerto se baseia na tabela abaixo: <br>[[imagem:Previsao-barometro.png|800px]]<br><br>Faça um algoritmo que forneça uma estimativa da previsão do tempo, usando essa tabela.
+
Para fazer um bom uso de estruturas de decisão deve-se primeiro conseguir identificar as condições a serem avaliadas. Condições são escritas com expressões lógicas, e estas são compostas de operadores lógicos e relacionais aplicados a variáveis e constantes.
# Faça um algoritmo que mostre qual o último dia de um determinado mês informado pelo teclado. Caso seja informado o mês 2 (fevereiro), seu algoritmo deve identificar se é [http://pt.wikipedia.org/wiki/Bissexto ano bissexto] (assim o mês tem 29 dias), ou não (mês tem 28 dias). Obs: anos bissextos são dados pelas regras (segundo o [http://pt.wikipedia.org/wiki/Calend%C3%A1rio_Gregoriano calendário Gregoriano]):
 
## De 400 em 400 anos é ano bissexto.
 
## De 100 em 100 anos não é ano bissexto.
 
## De 4 em 4 anos é ano bissexto.<br>''Solução vista em aula: (sem considerar anos bissextos):'' <syntaxhighlight lang=text>
 
inicio
 
      texto mes
 
     
 
      escrever "Mes: "
 
      ler mes
 
     
 
      escolhe mes
 
        caso "janeiro","março", "maio", "julho", "agosto", "outubro", "dezembro":
 
          escrever 31
 
        caso "abril", "junho", "setembro", "novembro":
 
          escrever 30
 
        caso "fevereiro":
 
          escrever 28
 
        defeito:
 
          escrever "mes desconhecido !"
 
      fimEscolhe
 
fim
 
</syntaxhighlight>
 
  
== 27/09: Estruturas de decisão ==
+
=== Condições ===
  
Na aula se fez a resolução de exercícios propostos.
+
Condições representam os testes que precisam ser feitos com dados do problema. Esses testes são expressados por '''''expressões lógicas''''', cujos resultados são ''verdadeiro'' ou ''falso''. Expressões lógicas são construídas usando-se '''''operadores lógicos''''' e '''''operadores relacionais''''' para comparar e avaliar os valores de variáveis e constantes.
* jogo de par ou ímpar <syntaxhighlight lang=text>
 
inicio
 
  inteiro numeroComputador
 
  inteiro numeroUsuario
 
  inteiro soma
 
  inteiro resto
 
  texto opcaoUsuario
 
 
 
  // sorteia um numero entre 0 e 10 para o computador
 
  // "aleatorio()" é uma função que gera um número real entre 0 e 1
 
  numeroComputador <- aleatorio()*10
 
 
 
  escrever "Escolha par ou impar: "
 
  ler opcaoUsuario
 
  
  escrever "Escolha seu numero: "
+
Obs: para os exemplos abaixo são usadas estas variáveis: <syntaxhighlight lang=text>
  ler numeroUsuario
+
Logico correto, multa, aprovado, barato, bombear_agua
 
+
Logico descartar, baixo, reprovado, erro, enviado, recebido
 
+
inteiro erros, pontuacao, preco, endereco, velocidade
  escrever "Numero do computador: ", numeroComputador
+
Real faltas, nivel_agua, altura
  escrever "\nNumero do usuario: ", numeroUsuario
 
 
 
  // Para fazer a verificacao do vencedor, precisa antes descobrir se
 
  // o resultado é par ou ímpar. O resultado se obtém somando os números do
 
  // computador e do usuário, e é guardado na variável "soma". Já a variável
 
  // "resto" contém 0 se o resultado for par, ou 1 se for ímpar.
 
  soma <- numeroUsuario + numeroComputador
 
  resto <- soma % 2
 
 
 
  // Verifica quem venceu: se o resultado for par e o usuário escolheu "par", ou se
 
  // o resultado for ímpar e o usuário escolheu ímpar, então o usuário venceu. Caso
 
  // contrário o computador é o vencedor.
 
  // Repare como se expressa a condição para descobrir o vencedor: ela usa
 
  // várias condições simples combinadas com operadores lógicos E e OU.
 
  se (resto = 0) E (opcaoUsuario = "par") OU (resto = 1) E (opcaoUsuario = "impar") entao
 
    escrever "\n\nUsuario venceu :-)"
 
  senao
 
    escrever "\n\nComputador venceu :-b"
 
  fimSe
 
 
 
fim
 
 
</syntaxhighlight>
 
</syntaxhighlight>
* leitura de três palavras e teste se ano menos duas pertencem a um conjunto: <syntaxhighlight lang=text>
 
// Neste algoritmo deve-se identificar se ao menos duas palavras
 
// diferentes têm os valores azul, preto ou vermelho.
 
// A variável inteira "cont" conta quantas palavras diferentes
 
// tem esses valores.
 
  
inicio
+
==== Operadores relacionais ====
    texto p1 , p2 , p3
+
 
    inteiro cont <- 0
+
Operadores relacionais são usados para comparar valores, e estão listados  na tabela abaixo. Cada comparação feita com esses operadores forma uma ''expressão lógica simples''. Portanto, o resultado de uma comparação é um valor lógico que pode ser ''verdadeiro'' ou ''falso''.
   
 
    escrever "Palavra 1: "
 
    ler p1
 
    escrever "Palavra 2: "
 
    ler p2
 
    escrever "Palavra 3: "
 
    ler p3
 
   
 
    // ao menos uma palavra é "azul" ?
 
    se p1 = "azul" OU p2 = "azul" OU p3 = "azul" entao
 
      cont <- 1
 
    fimse
 
  
    // ao menos uma palavra é "preto" ?
+
{| border="1" cellpadding="2"
    se p1 = "preto" OU p2 = "preto" OU p3 = "preto" entao
+
!Operador
      cont <- cont + 1
+
!Descrição
    fimse
+
!Exemplo
 +
|-
 +
|=||Igualdade|| correto <- (erros = 0)
 +
|-
 +
|>||Maior|| multa <- (velocidade > 80)
 +
|-
 +
|>=||Maior ou igual|| aprovado <- (pontuacao >= 70)
 +
|-
 +
|<||Menor|| barato <- (preco < 100)
 +
|-
 +
|<=||Menor ou igual|| bombear_agua <- (nivel_agua <= 0.7)
 +
|-
 +
|=/=||Diferente|| descartar <- (endereco =/= 12345)
 +
|}
  
    // ao menos uma palavra é "vermelho" ?
+
==== Operadores lógicos ====
    se p1 = "vermelho" OU p2 = "vermelho" OU p3 = "vermelho" entao
 
      cont <- cont + 1
 
    fimse
 
  
    // se duas ou mais palavras diferentes têm aqueles valores,
+
Operadores lógicos são usados para combinar expressões lógicas simples, criando assim ''expressões lógicas compostas'', e estão listados  na tabela abaixo.
    // então mostra VERDADEIRO
+
 
    se cont > 1 entao
+
{| border="1" cellpadding="2"
      escrever "VERDADEIRO"
+
!Operador
    senao
+
!Descrição
      escrever "FALSO"
+
!Exemplo
    fimse
+
|-
       
+
|NAO||Negação|| baixo <- NAO (altura > 1.8)
fim
+
|-
</syntaxhighlight>
+
|E||Conjunção|| aprovado <- NAO (conceito = "D") E (faltas <= 0.25)
* teste de ano bissexto, e seu uso para mostrar quantos dias tem cada mês de um determinado ano. <syntaxhighlight lang=text>
+
|-
inicio
+
|OU||Disjunção|| reprovado <- (conceito = "D") OU (faltas > 0.25)
      texto mes
+
|-
      inteiro ano
+
|XOU||Disjunção exclusiva|| erro <- enviado XOU recebido
     
+
|}
      escrever "Mes: "
 
      ler mes
 
     
 
      escolhe mes
 
        caso "janeiro","março", "maio", "julho", "agosto", "outubro", "dezembro":
 
          escrever 31
 
        caso "abril", "junho", "setembro", "novembro":
 
          escrever 30
 
        caso "fevereiro":
 
            escrever "Ano: "
 
            ler ano
 
           
 
            se ano % 400 = 0 ou ano % 4 = 0 e ano % 100 =/= 0 entao
 
                escrever 29
 
            senao
 
                escrever 28
 
            fimse
 
        defeito:
 
          escrever "mes desconhecido !"
 
      fimEscolhe
 
fim
 
</syntaxhighlight>
 
  
== 28/09: Estruturas de repetição ==
+
Precedência dos operadores (nesta ordem): NAO, E, OU e XOU
  
Alguns algoritmos vistos anteriormente possuem sequências repetitivas de instruções. Por exemplo, o algoritmo da média de quatro avaliações:
+
Lembre que a precedência pode ser modificada com o uso de parênteses.
  
<syntaxhighlight lang=text>
+
=== Atividades ===
Inicio
 
  real m1, m2, m3, m4
 
  real media
 
  
  escrever "Avaliação 1:"
+
# Faça um programa que leia um número e então informe se ele é par ou ímpar.
   Ler m1
+
# Um radar de trânsito faz a medição de velocidade de veículos e, dependendo do valor, calcula a multa a ser aplicada. Em uma determinada via esse radar foi configurado da seguinte forma:
   escrever "Avaliação 2:"
+
#* Se a velocidade for maior que 80 km/h, a multa é de R$ 360.
   Ler m2
+
#* Se a velocidade for maior que 60 km/h, a multa é de R$ 180.
   escrever "Avaliação 3:"
+
#* Se a velocidade for menor ou igual a 60 km/h, não há multa.<br><br>Escreva um algoritmo que calcule a multa de acordo com a velocidade de um veículo.
   Ler m3
+
# Faça um algoritmo que leia três números do teclado, e mostre o maior e menor números.
   escrever "Avaliação 4:"
+
# Escreva um  algoritmo  que faça o [[SOP-2010-2-sobral#20.2F09:_Estruturas_de_decis.C3.A3o|teste de risco de paciente cardíaco]], mostrado no início da aula.
   Ler m4
+
# Um estudo sobre sensibilidade de pessoas a temperaturas da água identificou que a maioria das pessoas considera fria a água com temperaturas abaixo de 25 graus, morna entre 25 e 30 graus, e quente acima de 30 graus. Escreva um algoritmo que mostre as palavras "fria", "morna" ou "quente" dependendo da temperatura da água que for informada.
 
+
# Em uma rede de computadores, o ''firewall'' restringe o acesso a Internet dependendo do horário e do tipo de usuário que faz o acesso. Os tipos de usuário abaixo têm as seguintes restrições:
   media <- (m1 + m2 + m3 + m4) / 4
+
#* Funcionario: apenas entre 0:00 e 7:30, entre 18:30 e 0:00, e entre 12:00 e 13:30
 
+
#* Financeiro: qualquer horario
   escrever "Média: ", media
+
#* Diretoria: qualquer horário<br>Escreva um algoritmo que informe se um acesso foi permitido, em função do horário e do tipo de usuário.
Fim
+
# Modifique o algoritmo acima para adicionar a seguinte restrição:
 +
#* Funcionario: nao pode acessar sites de jornal (ex: www.rbs.com.br)
 +
#* Financeiro: nao pode acessar sites de jornal durante o expediente
 +
#* Diretoria: sem restrições a sites
 +
# Faça um algoritmo para fazer a divisão de dois números reais. Antes de dividi-los deve ser feito um teste de validade. Caso não seja possível dividi-los, deve ser mostrada uma mensagem de erro. Se for possível, deve-se mostrar o resultado da divisão.
 +
# Faça um jogo de par ou ímpar, em que o jogador aposta contra o computador. O jogador deve digitar um número entre 0 e 5 e optar entre par ou ímpar. O computador deve sortear um número também entre 0 e 5. Se a paridade da soma dos números do jogador e do computador for a mesma que o jogador optou, então ele ganha a partida, senão o computador vence.
 +
# Escreva um algoritmo para identificar se há, dentre três palavras lidas do teclado, ao menos duas palavras distintas que pertençam ao conjunto {azul, preto, vermelho}. Exemplos:
 +
#* Se o usuário digitar ''verde'', ''preto'', ''vermelho'', o programa deve mostrar na tela ''verdadeiro''
 +
#* Se o usuário digitar ''verde'', ''preto'', ''preto'', o programa deve mostrar na tela ''falso''
 +
#* Se o usuário digitar ''azul'', ''preto'', ''azul'', o programa deve mostrar na tela ''verdadeiro''
 +
<syntaxhighlight lang=text>
 +
 
 +
inicio
 +
  texto cor1, cor2, cor3
 +
  inteiro cont <- 0
 +
   
 +
  ler cor1
 +
   ler cor2
 +
   ler cor3
 +
    
 +
   se cor1 = "preto" ou cor2 = "preto" ou cor3 = "preto" entao
 +
    cont <- cont + 1
 +
   fimse
 +
 
 +
   se cor1 = "azul" ou cor2 = "azul" ou cor3 = "azul" entao
 +
    cont <- cont + 1
 +
   fimse
 +
 
 +
   se cor1 = "vermelho" ou cor2 = "vermelho" ou cor3 = "vermelho" entao
 +
    cont <- cont + 1
 +
  fimse
 +
       
 +
  se cont > 1 entao
 +
    escrever "verdadeiro"
 +
   senao
 +
    escrever "falso"
 +
  fimse
 +
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
  
O algoritmo acima repete quatro vezes a sequência que lê uma nota do teclado. Porém há uma forma de expressar a repetição de sequências de instruções, usando-se o que se chama de ''estrutura de repetição''. A estrutura de repetição '''''enquanto''''' ''condição'' '''''faz''''' repete todas as instruções enquanto a condição for verdadeira. A condição é escrita como uma expressão lógica, da mesma forma que na estrutura de decisão '''''se''''' ''condição'' '''''então ... senão'''''. Veja como fica o algoritmo acima ao ser reescrito para usar essa estrutura de repetição:
+
=== Fluxogramas ===
  
<syntaxhighlight lang=text>
+
Diagramas de bloco para auxiliar a descrição de algoritmos. Ajudam na compreensão do algoritmo, por poder visualizar o fluxo de execução.
Inicio
 
  constante inteiro NUMEROS <- 4
 
  real m
 
  real media <- 0
 
  inteiro contador <- 0
 
  
  enquanto contador < NUMEROS faz 
 
    escrever "Avaliação ", contador, ":"
 
    ler m
 
    media <- media + m
 
    contador <- contador + 1
 
  fimEnquanto
 
  
  escrever "Média: ", media/NUMEROS
+
[[imagem:Fluxograma-soma.png]] Fluxograma para o algoritmo da média de trẽs números.
Fim
 
</syntaxhighlight>
 
  
Esse algoritmo funciona somente para médias de quatro números. Porém calcular a média de qualquer quantidade de números usa a mesma lógica: ler os números, somá-los e dividir o total pela quantidade de números lidos. Por exemplo, para fazer com que ele calcule a média de 7 números é necessário escrevê-lo assim:
+
<br>
  
<syntaxhighlight lang=text>
+
'''Blocos de uso mais comum'''<br>
Inicio
+
{| border="1" cellpadding="2"
  constante inteiro NUMEROS <- 7
+
!Bloco
  real m
+
!Descrição
  real media
+
!Exemplo
  inteiro contador <- 0
+
|-
 
+
|[[Imagem:Inicio.png]]||Inicio do fluxograma||
  enquanto contador < NUMEROS faz  
+
|-
    escrever "Avaliação ", contador, ":"
+
|[[Imagem:Processamento.png]]||Processamento||
    ler m
+
|-
    media <- media + m
+
|[[Imagem:Entrada.png]]||Entrada de dados (ler do teclado)||
    contador <- contador + 1
+
|-
  fimEnquanto
+
|[[Imagem:Saida.png]]||Saída de dados (mostrar na tela)||
 +
  |-
 +
|[[Imagem:Decisao.png]]||Decisão (testar uma condição e bifurcar)||[[imagem:Ex-decisao.png]]
 +
|-
 +
|[[Imagem:Conector.png]]||Conector (juntar dos ou mais ramos do fluxograma)||[[imagem:Ex-conector.png]]
 +
|-
 +
|[[Imagem:Fim.png]]||Fim||
 +
|}
  
  escrever "Média: ", media/NUMEROS
+
Obs: [http://www.sj.ifsc.edu.br/%7Emsobral/SOP/exemplos/fluxogramas.cfg Arquivo de configuração das cores do fluxograma ] do Portugol.
Fim
 
</syntaxhighlight>
 
  
Note que o algoritmo praticamente não foi modificado, pois somente se alterou o valor da constante NUMEROS.
+
== 20/04: estruturas de decisão ==
  
Esses dois algoritmos podem também ser visualizados como fluxogramas, como mostrado na figura abaixo:
+
Há situações em que se precisa fazer um conjunto de comparações, como mostrado abaixo:
 
 
[[imagem:Ex-repeticao.png]]
 
 
 
A estrutura de repetição junto com a sequência de instruções a ser repetida é comumente chamada de '''laço''. No fluxograma acima o laço está destacado em vermelho, e no algoritmo em Portugol o laço aparece em:
 
  
 
<syntaxhighlight lang=text>
 
<syntaxhighlight lang=text>
  enquanto contador < NUMEROS faz 
+
// Lê a data no formato numérico dia, mes, ano, e mostra a data no formato
    escrever "Avaliação ", contador, ":"
+
// dia, nome do mês, ano.
    ler m
+
Inicio
    media <- media + m
+
  inteiro dia, mes, ano
    contador <- contador + 1
+
   texto nome_mes
   fimEnquanto
 
</syntaxhighlight>
 
  
----
+
  escrever "Dia: "
 +
  ler dia
 +
  escrever "Mes: "
 +
  ler mes
 +
  escrever "Ano: "
 +
  ler ano
  
Um outro exemplo ainda mais simples é mostrar na tela uma contagem numérica:
+
  se mes = 1 entao
 
+
    nome_mes <- "Janeiro"
<syntaxhighlight lang=text>
+
  senao
inicio
+
     se mes = 2 entao
     inteiro contador
+
      nome_mes <- "Fevereiro"
    contador <- 0
+
    senao
 
+
      se mes = 3 entao
    enquanto contador < 10 faz
+
        nome_mes <- "Março"
         escrever contador , " "
+
      senao
         contador <- contador + 1
+
         se mes = 4 entao
    fimenquanto
+
          nome_mes <- "Abril"
fim
+
         senao
</syntaxhighlight>
+
          se mes = 5 entao
 
+
            nome_mes <- "Maio"
Ao executar esse algoritmo, tem-se como resultado:
+
          senao
 
+
            se mes = 6 entao
<syntaxhighlight lang=text>
+
              nome_mes <- "Junho"
0 1 2 3 4 5 6 7 8 9
+
            senao
</syntaxhighlight>
+
              se mes = 7 entao
 
+
                nome_mes <- "Julho"
Seu fluxograma está mostrado a seguir:
+
              senao
 
+
                se mes = 8 entao
[[imagem:Flux-Contagem.png]]
+
                  nome_mes <- "Agosto"
 +
              senao
 +
                  se mes = 9 entao
 +
                    nome_mes <- "Setembro"
 +
                  senao
 +
                    se mes = 10 entao
 +
                      nome_mes <- "Outubro"
 +
                    senao
 +
                      se mes = 11 entao
 +
                        nome_mes <- "Novembro"
 +
                      senao
 +
                        nome_mes <- "Dezembro"
 +
                      fimSe
 +
                    fimSe
 +
                  fimSe
 +
                fimSe
 +
              fimSe
 +
            fimSe
 +
          fimSe
 +
        fimSe
 +
      fimSe
 +
    fimSe
 +
  fimSe
  
 +
  escrever dia, " de ", nome_mes, " de ", ano
 +
fim
 +
</syntaxhighlight>
  
Repare no uso de uma variável auxiliar ''contador'' para controlar a quantidade de repetições. Essa é uma técnica comum para
+
Além de ser trabalhoso esse encadeamento de ''Se ... entao ... senao'', o algoritmo resultante fica pouco legível. Quer dizer, ele fica feio e difícil de entender.  
controlar a estrutura de repetição, e já foi usada no exemplo da média. Ela pode também ser combinada com outras condições, como mostrado abaixo:
+
 
 +
Existe uma estrutura de decisão criada justamente para casos como esse, e que resulta em um algoritmo mais limpo e compreensível:
  
 
<syntaxhighlight lang=text>
 
<syntaxhighlight lang=text>
inicio
+
// Lê a data no formato numérico dia, mes, ano, e mostra a data no formato
    inteiro contador <- 1
+
// dia, nome do mês, ano.
    caracter opcao <- "s"
+
Inicio
       
+
  inteiro dia, mes, ano
    enquanto ((opcao = "s") ou (opcao = "S")) e contador < 11 faz
+
  texto nome_mes
        escrever contador, "\n"
 
        contador <- contador + 1
 
       
 
        escrever "\nContinuar (S/N) ? "
 
        ler opcao
 
    fimenquanto
 
   
 
    escrever "Terminou com contador = " , contador
 
fim
 
</syntaxhighlight>
 
  
Nesse exemplo se usa um laço para mostrar uma contagem de 1 a 10. Porém há a possibilidade de encerrar o algoritmo. Observe a condição para continuidade do laço: ela é verdadeira somente se ''contador < 11'' e se a variável ''opcao'' for igual a "s" ou "S".
+
  escrever "Dia: "
 +
  ler dia
 +
  escrever "Mes: "
 +
  ler mes
 +
  escrever "Ano: "
 +
  ler ano
  
Finalmente, apesar de ser comum o uso de contadores para controle do laço, pode-se usar qualquer condição para essa finalidade. Então podem existir laços que não usam contadores para controlar a quantidade de repetições, como no próximo exemplo:
+
  Escolhe mes
 +
    caso 1:
 +
      nome_mes <- "Janeiro"
 +
    caso 2:
 +
      nome_mes <- "Fevereiro"
 +
    caso 3:
 +
      nome_mes <- "Março"
 +
    caso 4:
 +
      nome_mes <- "Abril"
 +
    caso 5:
 +
      nome_mes <- "Maio"
 +
    caso 6:
 +
      nome_mes <- "Junho"
 +
    caso 7:
 +
      nome_mes <- "Julho"
 +
    caso 8:
 +
      nome_mes <- "Agosto"
 +
    caso 9:  
 +
      nome_mes <- "Setembro"
 +
    caso 10:
 +
      nome_mes <- "Outubro"
 +
    caso 11:
 +
      nome_mes <- "Novembro"
 +
    Defeito:
 +
      nome_mes <- "Dezembro"
 +
  fimEscolhe
  
<syntaxhighlight lang=text>
+
  escrever dia, " de ", nome_mes, " de ", ano
inicio
+
fim
    constante texto segredo <- "secreto"
+
</syntaxhighlight>
    texto senha
+
 
   
+
A estrutura de decisão ''escolhe ... caso'' tem uma certa flexibilidade. No exemplo abaixo, mostra-se a possibilidade de testar mais de um valor no mesmo ''caso'':
    ler senha
 
    enquanto senha =/= segredo faz
 
        escrever "Voce continua preso ! Digite a senha correta: "
 
        ler senha
 
    fimenquanto
 
    escrever "Voce foi liberado ..."
 
fim
 
</syntaxhighlight>
 
  
O fluxograma desse algoritmo segue abaixo:
+
<syntaxhighlight lang=text>
 +
inicio   
 +
  caracter sexo   
  
[[imagem:Flux-Senha.png]]
+
  escrever "Qual o seu sexo (f/m):"   
 +
  ler sexo   
  
=== Atividades ===
+
  escrever "Olá "   
  
# Escreva um  algoritmo que mostre a tabuada de um número fornecido pelo teclado. Esse número deve estar entre 1 e 10.
+
  escolhe sexo       
# Aproveite o algoritmo anterior para mostrar a tabuada de todos os números entre 1 e 10.
+
    caso "m", "M" :            
# Modifique o exemplo da média para que a quantidade de números a serem lidos seja previamente informada pelo teclado.
+
      escrever "senhor"       
# Escreva  algoritmos que mostrem as seguintes sequências de números:
+
    caso "f","F" :            
#* Números pares menores que 100
+
      escrever "senhorita"       
#* Números ímpares menores que 100
+
    defeito :            
#* Números pares de 100 até 4 (contagem decrescente)
+
      escrever "Sexo indefinido"   
#* Múltiplos de 3 menores que 100
+
  fimescolhe   
#* Múltiplos de 4 e múltiplos de 5 menores que 100
 
#* Múltiplos comuns menores que 1000 de dois números fornecidos pelo teclado (ex: se forem  fornecidos 6 e 8, deve aparecer 24, 48, 72, ...)
 
# Modifique novamente o exemplo da média para que ela funcione para um quantidade de números desconhecida de antemão. Quer dizer, o algoritmo deve ler os números para calcular a média, mas não sabe quantos números existem (e isto não pode ser informado pelo teclado).
 
# Modifique o exemplo da senha para que o usuário tenha somente três tentativas permitidas para digitar a senha correta. Caso ao final as três senhas estejam erradas, o algoritmo deve informar que a conta foi bloqueada.
 
# Escreva um algoritmo que leia até 10 números do teclado, e informe ao final qual o maior e o menor deles.
 
# Escreva um algoritmo que teste se um número informado pelo teclado é primo.
 
# Aproveite o algoritmo do ítem anterior para mostrar todos os números primos menores que 1000.
 
# Usando o algoritmo de teste de número primo, faça um novo algoritmo que fatore um número. Ex: a fatoração do número 15 resulta em  3 e 5 (3 X 5), e a fatoração de 54 resulta em 2, 3, 3 e 3 (2 X 3 X 3 X 3).
 
# Usando estrutura de repetição, escreva um algoritmo que converta um número de decimal para binário. Assuma um número binário com 16 bits.
 
# Escreva um algoritmo para calcular o MMC (Mínimo Múltiplo Comum) de dois números. O MMC de dois números é um número que pode ser dividido por qualquer um deles sem deixar resto. Ex:
 
#* MMC de 8 e 6 = 24
 
#* MMC de 3 e 5 = 15
 
#* MMC de 3 e 27 = 27
 
# Escreva um  algoritmo para calcular o MDC (Máximo Divisor Comum) de dois números. O MDC de dois números é um número capaz de dividi-los sem deixar resto. Ex:
 
#* MDC de 24 e 16 = 8
 
#* MDC de 5 e 3 = 1
 
#* MDC de 60 e 150 = 30
 
# Faça um algoritmo para descobrir os dois maiores números dentre 6 números lidos do teclado.
 
# Faça um algoritmo para converter um número entre 0 e 16777215 para sua representação em hexadecimal.
 
# Escreva o algoritmo para uma calculadora aritmética (operações +, -, * e /) que lê continuamente do teclado números e operadores. A calculadora deve ler continuamente uma sequência do tipo ''número operador_aritmético'', até que o operador informado seja ''='', quando então o resultado da conta deve ser mostrado na tela. Ex:
 
#* 1 + 2 * 5 / 3 = 5
 
#* 2 * 5 - 1 / 3 = 3
 
  
== 04/10: Estruturas de repetição ==
+
  escrever ", benvindo ao portugol"
 
+
fim
Resolução de exercícios
+
</syntaxhighlight>
  
== 05/10: Estruturas de repetição ==
+
=== Atividades ===
  
Resolução de exercícios
+
# Faça um algoritmo que converta um número de 1 a 7 para o respectivo dia da semana (ex: 1 = domingo, 2 = 2a feira, e assim por diante).
 +
# Faça uma calculadora com as quatro operações aritméticas. Sua calculadora deve ler (nesta ordem) o primeiro número, a operação aritmética (que deve ser informada usando o símbolo da respectiva operação: +, -, * ou /), e depois o segundo número. Ao final, seu algoritmo deve mostrar o resultado, ou uma mensagem de erro se a operação não for possível de realizar (ex: divisão por zero).
 +
# A previsão do tempo na costa brasileira pode ser feita de forma aproximada usando-se um barômetro e um termômetro. Uma estimativa com boa chance de acerto se baseia na tabela abaixo: <br>[[imagem:Previsao-barometro.png|800px]]<br><br>Faça um algoritmo que forneça uma estimativa da previsão do tempo usando essa tabela.
 +
# Faça um algoritmo que mostre qual o último dia de um determinado mês informado pelo teclado. Caso seja informado o mês 2 (fevereiro), seu algoritmo deve identificar se é [http://pt.wikipedia.org/wiki/Bissexto ano bissexto] (assim o mês tem 29 dias), ou não (mês tem 28 dias). Obs: anos bissextos são dados pelas regras (segundo o [http://pt.wikipedia.org/wiki/Calend%C3%A1rio_Gregoriano calendário Gregoriano]):
 +
## De 400 em 400 anos é ano bissexto.
 +
## De 100 em 100 anos não é ano bissexto.
 +
## De 4 em 4 anos é ano bissexto.<br>''Solução vista em aula: (sem considerar anos bissextos):''
  
== 18/10: Estruturas de repetição  ==
+
== 27/04: Estruturas de decisão ==
  
=== Para ''variavel'' de ''inicio'' ate ''fim'' passo ''incremento'' ===
+
=== Exercícios ===
  
Há casos em que se deseja repetir uma parte de um algoritmo certo número de vezes. Para esses casos há uma estrutura mais prática que ''enquanto condição faz'':
+
# Um estudo sobre sensibilidade de pessoas a temperaturas da água identificou que a maioria das pessoas considera fria a água com temperaturas abaixo de 25 graus, morna entre 25 e 30 graus, e quente acima de 30 graus. Escreva um algoritmo que mostre as palavras "fria", "morna" ou "quente" dependendo da temperatura da água que for informada.
 +
# Faça um algoritmo para fazer a divisão de dois números reais. Antes de dividi-los deve ser feito um teste de validade. Caso não seja possível dividi-los, deve ser mostrada uma mensagem de erro. Se for possível, deve-se mostrar o resultado da divisão.
 +
# Escreva um programa que leia cinco números do teclado e mostre os dois maiores números.
 +
# Faça um  programa que leia o nome de um usuário e sua senha, e em seguida informe se o acesso foi concedido ou negado. Os usuários possíveis de entrar são "joao", "maria" e "zé".
 +
# Jogo de Pedra, papel e tesoura: nesse jogo cada jogador faz sua escolha, e vence aquele que escolher um objeto que seja capaz de vencer o outro:
 +
#* Tesoura corta papel
 +
#* Pedra quebra tesoura
 +
#* Papel embrulha a pedra<br>Faça um algoritmo que pergunte ao usuário o objeto escolhido, e em seguida faça o computador escolher o seu próprio objeto (dica: use o gerador de números aleatórios visto no jogo do par ou ímpar). Finalmente o algoritmo deve informar o vencedor.
  
<syntaxhighlight lang=text>
+
== 28/04: Estruturas de repetição ==
inicio
 
  inteiro i
 
  inteiro v[5]
 
  
  escrever "Digite 5 números: \n"
+
Alguns algoritmos vistos anteriormente possuem sequências repetitivas de instruções. Por exemplo, o algoritmo da média de quatro avaliações:
  
   para i de 0 ate 4 passo 1
+
<syntaxhighlight lang=text>
    escrever "Numero ", i, ": "
+
Inicio
    ler v[i]
+
   real m1, m2, m3, m4
   proximo
+
   real media
  
   escrever "\nOs numeros em ordem inversa são:\n\n"
+
   escrever "Avaliação 1:"
 +
  Ler m1
 +
  escrever "Avaliação 2:"
 +
  Ler m2
 +
  escrever "Avaliação 3:"
 +
  Ler m3
 +
  escrever "Avaliação 4:"
 +
  Ler m4
  
   para i de 4 ate 0 passo -1
+
   media <- (m1 + m2 + m3 + m4) / 4
    escrever "Numero ", i, ": ", v[i], "\n"
 
  proximo
 
  
fim
+
  escrever "Média: ", media
 +
Fim
 
</syntaxhighlight>
 
</syntaxhighlight>
  
=== Atividades ===
+
O algoritmo acima repete quatro vezes a sequência que lê uma nota do teclado. Porém há uma forma de expressar a repetição de sequências de instruções, usando-se o que se chama de ''estrutura de repetição''. A estrutura de repetição '''''enquanto''''' ''condição'' '''''faz''''' repete todas as instruções enquanto a condição for verdadeira. A condição é escrita como uma expressão lógica, da mesma forma que na estrutura de decisão '''''se''''' ''condição'' '''''então ... senão'''''. Veja como fica o algoritmo acima ao ser reescrito para usar essa estrutura de repetição:
  
# Escreva o algoritmo para comparar dois vetores, porém usando a estrutura ''para''.
+
<syntaxhighlight lang=text>
# Escreva um algoritmo para procurar se um vetor menor (com menos valores) está contido em um vetor maior. Caso afirmativo, mostre a partir de que posição ele aparece. Assuma vetores de números inteiros.
+
Inicio
# Modifique o algoritmo acima para mostrar todas as ocorrências do vetor menor dentro do maior.
+
  constante inteiro NUMEROS <- 4
# Modifique o algoritmo do anterior para remover todas as ocorrências do vetor menor dentro do maior.
+
  real m
# Resolva o problema do bingo usando a estrutura ''para''
+
  real media <- 0
 +
  inteiro contador <- 0
  
== 19/10: Estruturas de repetição ==
+
  enquanto contador < NUMEROS faz 
 
+
    escrever "Avaliação ", contador, ":"
 
+
    ler m
=== Variáveis multidimensionais ===
+
    media <- media + m
 +
    contador <- contador + 1
 +
  fimEnquanto
  
Em matemática existem matrizes e vetores, que são variáveis multidimensionais. Por exemplo, uma matriz 3 x 3 (3 linhas e 3 colunas) pode ser:
+
  escrever "Média: ", media/NUMEROS
 +
Fim
 +
</syntaxhighlight>
  
<math>A = \begin{pmatrix}
+
Esse algoritmo funciona somente para médias de quatro números. Porém calcular a média de qualquer quantidade de números usa a mesma lógica: ler os números, somá-los e dividir o total pela quantidade de números lidos. Por exemplo, para fazer com que ele calcule a média de 7 números é necessário escrevê-lo assim:
1 & 6 \\
 
3 & 5
 
\end{pmatrix}</math>
 
  
Vetores são matrizes unidimensionais, portanto possuem somente uma linha ou uma coluna:
+
<syntaxhighlight lang=text>
 +
Inicio
 +
  constante inteiro NUMEROS <- 7
 +
  real m
 +
  real media
 +
  inteiro contador <- 0
  
<math>v = \begin{pmatrix}
+
  enquanto contador < NUMEROS faz 
1 & 6 & 2 & 18 & 5
+
    escrever "Avaliação ", contador, ":"
\end{pmatrix}</math>
+
    ler m
 +
    media <- media + m
 +
    contador <- contador + 1
 +
  fimEnquanto
  
Cada elemento em uma matriz ou vetor é identificado pela sua posição. Por exemplo, na posição ''1, 2'' da matriz A acima está o valor 6, e na posição ''4'' do vetor ''v'' está o valor 18. Assim, a matriz A do exemplo pode ser entendida da seguinte forma:
+
  escrever "Média: ", media/NUMEROS
 +
Fim
 +
</syntaxhighlight>
  
<math>A = \begin{pmatrix}
+
Note que o algoritmo praticamente não foi modificado, pois somente se alterou o valor da constante NUMEROS.
A_{11} & A_{12} \\
 
A_{21} & A_{22}
 
\end{pmatrix}</math>
 
  
... e o vetor ''v'' do exemplo:
+
Esses dois algoritmos podem também ser visualizados como fluxogramas, como mostrado na figura abaixo:
  
<math>v = \begin{pmatrix}
+
[[imagem:Ex-repeticao.png]]
v_{1} & v_{2} & v_{3} & v_{4} & v_{5}
 
\end{pmatrix}</math>
 
  
Nas linguagens de programação em geral existe um conceito muito parecido, chamado de variáveis multidimensionais ou simplesmente ''matrizes'' (''arrays'' em inglẽs). Para exemplificar, no Portugol se poderiam definir a matriz ''A'' e o vetor ''v'':
+
A estrutura de repetição junto com a sequência de instruções a ser repetida é comumente chamada de '''laço''. No fluxograma acima o laço está destacado em vermelho, e no algoritmo em Portugol o laço aparece em:
  
 
<syntaxhighlight lang=text>
 
<syntaxhighlight lang=text>
inicio
+
   enquanto contador < NUMEROS faz 
   inteiro A[2][2] <- {{1, 6}, {3, 5}}
+
    escrever "Avaliação ", contador, ":"
  inteiro M[3][2]
+
    ler m
  inteiro v[5] <- {1, 6, 2, 18, 5}
+
    media <- media + m
 +
    contador <- contador + 1
 +
  fimEnquanto
 +
</syntaxhighlight>
  
  escrever "Valor de A[0][0]: ", A[0][0], "\n"
+
----
  escrever "Valor de A[0][1]: ", A[0][1], "\n"
 
  escrever "Valor de A[1][0]: ", A[1][0], "\n"
 
  escrever "Valor de A[1][1]: ", A[1][1], "\n"
 
  
  escrever "Valor de v[0]: ", v[0], "\n"
+
Um outro exemplo ainda mais simples é mostrar na tela uma contagem numérica:
  escrever "Valor de v[1]: ", v[1], "\n"
+
 
  escrever "Valor de v[2]: ", v[2], "\n"
+
<syntaxhighlight lang=text>
  escrever "Valor de v[3]: ", v[3], "\n"
+
inicio
  escrever "Valor de v[4]: ", v[4], "\n"
+
    inteiro contador
 +
    contador <- 0
  
 +
    enquanto contador < 10 faz
 +
        escrever contador , " "
 +
        contador <- contador + 1
 +
    fimenquanto
 
fim
 
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
  
A declaração da matriz se faz como uma variável comum, porém indicando-se suas dimensões:
+
Ao executar esse algoritmo, tem-se como resultado:
  
 
<syntaxhighlight lang=text>
 
<syntaxhighlight lang=text>
  inteiro A[2][2] <- {{1, 6}, {3, 5}}
+
0 1 2 3 4 5 6 7 8 9
  inteiro M[3][2];
 
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Veja que a matriz ''M'' foi declarada sem valores iniciais, porém a matriz ''A'' foi inicializada na declaração.
+
Seu fluxograma está mostrado a seguir:
  
O acesso aos elementos da matriz se faz usando-se ''índices'', que funcionam como coordenadas dos elementos que se quer acessar. Os índices iniciam em ''0'':
+
[[imagem:Flux-Contagem.png]]
  
<syntaxhighlight lang=text>
 
  # índice 0,0
 
  escrever "Valor de A[0][0]: ", A[0][0], "\n"
 
</syntaxhighlight>
 
  
O exemplo acima pode ser reescrito usando-se estruturas de repetição:
+
Repare no uso de uma variável auxiliar ''contador'' para controlar a quantidade de repetições. Essa é uma técnica comum para
 +
controlar a estrutura de repetição, e já foi usada no exemplo da média. Ela pode também ser combinada com outras condições, como mostrado abaixo:
  
 
<syntaxhighlight lang=text>
 
<syntaxhighlight lang=text>
 
inicio
 
inicio
  inteiro A[2][2] <- {{1, 6}, {3, 5}}
+
    inteiro contador <- 1
  inteiro v[5] <- {1, 6, 2, 18, 5}
+
    caracter opcao <- "s"
  inteiro i, j
+
       
 
+
     enquanto ((opcao = "s") ou (opcao = "S")) e contador < 11 faz
  enquanto i < 2 faz
+
        escrever contador, "\n"
    j <- 0
+
        contador <- contador + 1
     enquanto j < 2 faz
+
       
      escrever "Valor do elemento de A na posição ", i, ", ", j, ": ", A[i][j], "\n"
+
        escrever "\nContinuar (S/N) ? "
      j <- j + 1
+
        ler opcao
 
     fimenquanto
 
     fimenquanto
     i <- i + 1
+
      
  fimenquanto
+
     escrever "Terminou com contador = " , contador
 
 
  i <- 0
 
  enquanto i < 5 faz
 
     escrever "valor de v na posição ", i, ": ", v[i], "\n"
 
    i <- i + 1
 
  fimenquanto
 
 
 
 
fim
 
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Como se vê, matrizes e vetores casam perfeitamente com estruturas de repetição, e são úteis para a resolução de inúmeros problemas. Por exemplo, o problema de mostrar o nome do mês a partir do número do mês, feito anteriormente com ''escolhe ... caso'' pode ser feito assim com um vetor:
+
Nesse exemplo se usa um laço para mostrar uma contagem de 1 a 10. Porém há a possibilidade de encerrar o algoritmo. Observe a condição para continuidade do laço: ela é verdadeira somente se ''contador < 11'' e se a variável ''opcao'' for igual a "s" ou "S".
 +
 
 +
Finalmente, apesar de ser comum o uso de contadores para controle do laço, pode-se usar qualquer condição para essa finalidade. Então podem existir laços que não usam contadores para controlar a quantidade de repetições, como no próximo exemplo:
  
 
<syntaxhighlight lang=text>
 
<syntaxhighlight lang=text>
 
inicio
 
inicio
  texto nome_mes[12] <- {"Janeiro", "Fevereiro", "Março", "Abril", "Maio", "Junho",
+
    constante texto segredo <- "secreto"
                        "Julho", "Agosto", "Setembro", "Outubro", "Novembro",
+
    texto senha
                        "Dezembro"}
+
   
  inteiro dia, mes, ano
+
    ler senha
 
+
    enquanto senha =/= segredo faz
  escrever "Dia: "
+
        escrever "Voce continua preso ! Digite a senha correta: "
  ler dia
+
        ler senha
  escrever "Mes: "
+
    fimenquanto
  ler mes
+
    escrever "Voce foi liberado ..."
  escrever "Ano: "
 
  ler ano
 
 
 
  escrever dia, " de ", nome_mes[mes - 1], " de ", ano
 
 
fim
 
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Outro problema comum é precisar guardar um conjunto de valores, e depois ordená-los:
+
O fluxograma desse algoritmo segue abaixo:
 +
 
 +
[[imagem:Flux-Senha.png]]
  
<syntaxhighlight lang=text>
+
=== Atividades ===
inicio
 
  inteiro v[10]
 
  inteiro i
 
  inteiro quantidade
 
  
  escrever "Quantos valores serão digitados (máximo = 10) ? "
+
# Escreva um  algoritmo que mostre a tabuada de um número fornecido pelo teclado. Esse número deve estar entre 1 e 10.
  ler quantidade
+
# Aproveite o algoritmo anterior para mostrar a tabuada de todos os números entre 1 e 10.
 
+
# Modifique o exemplo da média para que a quantidade de números a serem lidos seja previamente informada pelo teclado.
  i <- 0
+
# Escreva  algoritmos que mostrem as seguintes sequências de números:
  enquanto i < quantidade faz
+
#* Números pares menores que 100
     escrever "valor ", i, ": "
+
#* Números ímpares menores que 100
     ler v[i]
+
#* Números pares de 100 até 4 (contagem decrescente)
     i <- i + 1
+
#* Múltiplos de 3 menores que 100
  fimenquanto
+
#* Múltiplos de 4 e múltiplos de 5 menores que 100
 
+
#* Múltiplos comuns menores que 1000 de dois números fornecidos pelo teclado (ex: se forem  fornecidos 6 e 8, deve aparecer 24, 48, 72, ...)<syntaxhighlight lang=text>
  // ordena os valores ...
+
inicio
 
+
    inteiro n <- 0 , n1 , n2, mmc
  escrever "valores ordenados: "
+
   
  i <- 0
+
     escrever "Primeiro numero : "
  enquanto i < quantidade
+
    ler n1
    escrever v[i], " "
+
    escrever "Segundo numero : "
    i <- i + 1
+
     ler n2
  fimenquanto
+
      
 +
    // descobre o mmc de n1 e n2
 +
    se n1 > n2 entao
 +
      mmc <- n1
 +
    senao
 +
      mmc <- n2
 +
    fimse
 +
   
 +
    enquanto mmc % n1 =/= 0 OU mmc % n2 =/= 0 faz
 +
      mmc <- mmc + 1
 +
    fimenquanto
 +
   
 +
    // mostra os multiplos de mmc que sejam <= 1000
 +
    enquanto n <= 1000 faz
 +
        escrever "\n " , n
 +
        n <- n + mmc
 +
    fimenquanto
 
fim
 
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
 
+
# Escreva um algoritmo para calcular o MMC (Mínimo Múltiplo Comum) de dois números. O MMC de dois números é um número que pode ser dividido por qualquer um deles sem deixar resto. Ex:
=== Atividades ===
+
#* MMC de 8 e 6 = 24
 
+
#* MMC de 3 e 5 = 15
# Escreva um algoritmo que leia 5 números do teclado, e depois mostre-os em ordem inversa à que foi digitada.
+
#* MMC de 3 e 27 = 27
# Escreva um algoritmo que leia dois vetores de 5 números, e depois mostre se os vetores são iguais. <br><br>''Solução vista em aula:''<syntaxhighlight lang=text>
+
# Escreva um algoritmo para calcular o MDC (Máximo Divisor Comum) de dois números. O MDC de dois números é um número capaz de dividi-los sem deixar resto. Ex:
 +
#* MDC de 24 e 16 = 8
 +
#* MDC de 5 e 3 = 1
 +
#* MDC de 60 e 150 = 30<syntaxhighlight lang=text>
 
inicio
 
inicio
  inteiro v1[5]
+
    inteiro n1 , n2, mdc
  inteiro v2[5]
+
  inteiro n
+
    escrever "Primeiro numero : "
 +
    ler n1
 +
    escrever "Segundo numero : "
 +
    ler n2
 +
 +
    // descobre o mmc de n1 e n2
 +
    se n1 > n2 entao
 +
      mdc <- n2
 +
    senao
 +
      mdc <- n1
 +
    fimse
  
  // Le os valores do primeiro vetor
+
     enquanto mdc > 1 E NAO (n1 % mdc = 0 E n2 % mdc = 0) faz
  para n de 0 ate 4 passo 1
+
      mdc <- mdc - 1
     escrever "v1[", n, "]: "
+
    fimenquanto
    ler v1[n]
+
    
  proximo
+
     escrever "MDC=", mdc
 
+
fim
  // Le os valores do segundo vetor
 
  para n de 0 ate 4 passo 1
 
    escrever "v2[", n, "]: "
 
    ler v1[n]
 
  proximo
 
 
 
  // compara os dois vetores
 
  n <- 0
 
  enquanto n < 5 E v1[n] = v2[n] faz
 
    n <- n + 1
 
  fimenquanto
 
 
 
   // mostra o resultado da comparação
 
  se n = 5 entao
 
     escrever "Vetores iguais"
 
  senao
 
    escrever "Vetores diferem na posicao ", n
 
  fimse
 
fim
 
 
</syntaxhighlight>
 
</syntaxhighlight>
 +
# Escreva um algoritmo que leia até 10 números do teclado, e informe ao final qual o maior e o menor deles.
 +
# Escreva um algoritmo que teste se um número informado pelo teclado é primo.
 +
# Aproveite o algoritmo do ítem anterior para mostrar todos os números primos menores que 1000.
 +
# Modifique novamente o exemplo da média para que ela funcione para um quantidade de números desconhecida de antemão. Quer dizer, o algoritmo deve ler os números para calcular a média, mas não sabe quantos números existem (e isto não pode ser informado pelo teclado).
 +
# Modifique o exemplo da senha para que o usuário tenha somente três tentativas permitidas para digitar a senha correta. Caso ao final as três senhas estejam erradas, o algoritmo deve informar que a conta foi bloqueada.
 +
# Usando o algoritmo de teste de número primo, faça um novo algoritmo que fatore um número. Ex: a fatoração do número 15 resulta em  3 e 5 (3 X 5), e a fatoração de 54 resulta em 2, 3, 3 e 3 (2 X 3 X 3 X 3).
 +
# Usando estrutura de repetição, escreva um algoritmo que converta um número de decimal para binário. Assuma um número binário com 16 bits.
 +
# Faça um algoritmo para descobrir os dois maiores números dentre 6 números lidos do teclado.
 +
# Faça um algoritmo para converter um número entre 0 e 16777215 para sua representação em hexadecimal.
 +
# Escreva o algoritmo para uma calculadora aritmética (operações +, -, * e /) que lê continuamente do teclado números e operadores. A calculadora deve ler continuamente uma sequência do tipo ''número operador_aritmético'', até que o operador informado seja ''='', quando então o resultado da conta deve ser mostrado na tela. Ex:
 +
#* 1 + 2 * 5 / 3 = 5
 +
#* 2 * 5 - 1 / 3 = 3
  
# Escreva um algoritmo que leia um palavra do teclado e depois procure-a numa lista de palavras preexistente. Essa lista deve ser implementada usando um vetor.
+
== 04/05: Estruturas de repetição ==
# Escreva um algoritmo que leia 5 números, e mostre-os em ordem crescente.
 
# Modifique o algoritmo anterior para mostrá-los em ordem decrescente.
 
# Em um  jogo de bingo devem-se contar quantos números de uma aposta foram sorteados no bingo. Faça um algoritmo que, dados os números sorteados e uma aposta, conta quantos números apostados foram sorteados.
 
  
== 25/10: 2a avaliação ==
+
Resolução de exercícios (continuando aula anterior).
  
Avaliação em aula, no laboratório de Redes. Resolver usando o Portugol. Compactar os arquivos com os algoritmos e entregar para o professor.
+
== 05/05: Estruturas de repetição ==
  
Obs: para compactar:
+
Continuando a [[PRG-2011-1-sobral#Atividades_4|resolução de exercícios ...]]
  
<syntaxhighlight lang=bash>
+
=== Uma pequena avaliação ===
tar czf prova2-seu_nome.tgz *.alg
 
</syntaxhighlight>
 
  
Você precisará [[SOP-2010-2-sobral#Guia_r.C3.A1pido_de_instala.C3.A7.C3.A3o_e_utiliza.C3.A7.C3.A3o_do_Portugol|instalar o Portugol]] em seu computador.
+
Resolva o seguinte problema em 15 minutos:
  
1) '''Contador de moedas:''' faça um programa que leia valores de moedas e some as quantidades de tipos de moedas informadas. Por exemplo, se o usuário digitar 25, 50, 25, 5, 10, 5, o programa deve informar: ''2 moedas de 5 centavos, 1 moeda de 10 centavos, 2 moedas de 25 centavos, 1 moeda de 50 centavos''. São aceitos apenas valores de moedas de 1, 5, 10, 25 e 50 centavos. Seu programa deve ler 10 valores de moedas, e então apresentar o resultado.
+
'''Contador de moedas:''' faça um programa que leia valores de moedas e some as quantidades de tipos de moedas informadas. Por exemplo, se o usuário digitar 25, 50, 25, 5, 10, 5, o programa deve informar: 2 moedas de 5 centavos, 1 moeda de 10 centavos, 2 moedas de 25 centavos, 1 moeda de 50 centavos. São aceitos apenas valores de moedas de 1, 5, 10, 25 e 50 centavos. Seu programa deve ler 10 valores de moedas, e então apresentar o resultado.
  
2) '''Calculadora de troco:''' escreva um programa que calcule o troco a ser devolvido a um cliente. O troco deve ser composto de notas de 50, 20, 10, 5, 2 ou 1 real, e também moedas de 1, 5, 10, 25 ou 50 centavos. Dê preferência ao uso de notas e moedas de maior valor. Por exemplo, se o troco a ser devolvido for ''R$ 17,75'', seu programa deve informar ''1 nota de R$ 10, 1 nota de R$ 5, 1 nota de R$ 2, 1 moeda de R$ 0,50, 1 moeda de R$ 0,25''.<syntaxhighlight lang=text>Inicio
+
<syntaxhighlight lang=text>
   inteiro notas[6] <- {50,20,10,5,2,1}
+
inicio
   inteiro moedas[5] <- {50,25,10,5,1}
+
   inteiro m1, m5, m10, m25, m50
   inteiro reais, centavos
+
   inteiro moeda
  inteiro i, aux
+
   inteiro n
    
+
   
  escrever "Reais: "
+
   enquanto n < 10 faz
  ler reais
+
    escrever "Moeda: "
  escrever "Centavos: "
+
    ler moeda
  ler centavos
+
   
 
+
    escolhe moeda
  para i de 0 ate 5 passo 1
+
      caso 1:
    aux <- reais / notas[i]
+
        m1 <- m1 + 1
    se aux > 0 entao
+
      caso 5:
       escrever aux, " notas de R$ ", notas[i], "\n"
+
        m5 <- m5 + 1
      reais <- reais % notas[i]
+
      caso 10:
     fimse
+
        m10 <- m10 + 1
   proximo
+
      caso 25:
 
+
        m25 <- m25 + 1
   para i de 0 ate 4 passo 1
+
      caso 50:
    aux <- centavos / moedas[i]
+
        m50 <- m50 + 1
    se aux > 0 entao
+
       defeito:
      escrever aux, " moedas de R$ 0,", moedas[i], "\n"
+
        escrever "Valor invalido ...\n"
      centavos <- centavos % moedas[i]
+
        n <- n - 1
    fimse
+
     fimescolhe
  proximo
+
    n <- n + 1
 
+
   fimenquanto
 +
 
 +
   escrever "Moedas de 1 centavo: ", m1
 +
  escrever "\nMoedas de 5 centavos: ", m5
 +
  escrever "\nMoedas de 10 centavos: ", m10 
 +
  escrever "\nMoedas de 25 centavos: ", m25
 +
  escrever "\nMoedas de 50 centavos: ", m50
 
fim
 
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
  
3) '''Modificação de senha:''' Para modificar uma senha deve-se primeiro fornecer a senha
+
== 11/05: Estruturas de repetição ==
atual, e então a nova senha.  É necessário escrever duas vezes a nova
 
senha para confirmá-la. Escreva um  algoritmo  que modifique uma senha
 
predefinida (no seu programa ela pode estar guardada em uma variável), seguindo essa regra de mudança de senha.
 
  
4) '''Nota de uma prova olímpica:''' um atleta de saltos ornamentais tem seu salto avaliado por 6 juízes. Após descartar a maior e a menor nota, calcula-se a média aritmética das notas dadas. Faça um programa que calcule a nota de um  atleta.
 
  
=== Conceitos da 2a avaliação ===
+
=== Variáveis multidimensionais ===
  
 +
Em matemática existem matrizes e vetores, que são variáveis multidimensionais. Por exemplo, uma matriz 2 x 2 (2 linhas e 2 colunas) pode ser:
  
''Legenda:''
+
<math>A = \begin{pmatrix}
*'''T:''' Atendeu a questão totalmente
+
1 & 6 \\
*'''P:''' Atendeu parcialmente
+
3 & 5
*'''N:''' Não atendeu
+
\end{pmatrix}</math>
*''Sufixo +:'' apresentou uma boa solução
 
*''Sufixo -:'' apresentou uma solução que não escolheu estruturas de controle mais adequadas
 
  
 +
Vetores são matrizes unidimensionais, portanto possuem somente uma linha ou uma coluna:
  
{| border="1" cellpadding="2"
+
<math>v = \begin{pmatrix}
!Aluno
+
1 & 6 & 2 & 18 & 5
!Questão 1
+
\end{pmatrix}</math>
!Questão 2  
 
!Questão 3
 
!Questão 4
 
!Conceito
 
|-
 
|Fernando || N || N || T- ''(testes redundantes da senha atual)''|| T || C
 
|-
 
|Gabriel || || || || || D (ausente)
 
|-
 
|Levi || || || || || D (ausente)
 
|-
 
|Lindalvo || T ''(faltou testar se a moeda é válida)'' || N || T || T || A
 
|-
 
|Marcos || T- ''(faltou testar se a moeda é válida, algoritmo muito extenso ...)''|| N || T || N || C
 
|-
 
|Marine || T+ || T || T || N || A
 
|-
 
|Mario Allan || T || N || T ''(algoritmo nunca termina !)''|| N || C
 
|-
 
|Mário André || T ''(faltou testar se a moeda é válida)'' || T || T+ || N || A
 
|-
 
|Mário Sérgio || N || N || N || N || D
 
|-
 
|Maykon || T- ''(erro no  teste de moeda válida)''|| N || T || N ''(não identificou maior e menor notas)''|| C
 
|-
 
|Nathany || N || N || T || T- ''(não identifica a menor nota)''|| C
 
|-
 
|Pamella || || || || || D (ausente)
 
|-
 
|Paulo Igor || T- ''(não mostra moedas de 1 centavo, lê 11 moedas)''|| N || N || N || D
 
|-
 
|Ricardo || N || N || P ''(não confere a senha atual)''|| N || D
 
|-
 
|Roberto || || || || || D (ausente)
 
|-
 
|Thiago Martins || || || || || D (ausente)
 
|-
 
|Thiago Ramos || N || N || N || N || D
 
|-
 
|Vinicius Kachniacz || N || N || N || N || D
 
|-
 
|Vinicius Rodrigues || N || N || N ''(não confere as senhas)'' || N ''(não exclui maior e menor notas)''|| D
 
|-
 
|}
 
  
= Linguagem C: Projeto final =
+
Cada elemento em uma matriz ou vetor é identificado pela sua posição. Por exemplo, na posição ''1, 2'' da matriz A acima está o valor 6, e na posição ''4'' do vetor ''v'' está o valor 18. Assim, a matriz A do exemplo pode ser entendida da seguinte forma:
  
== 26/10:  Introdução à linguagem C ==
+
<math>A = \begin{pmatrix}
 
+
A_{11} & A_{12} \\
* Baseado no [[Guia Básico de C]].
+
A_{21} & A_{22}
* Para provocar: [http://norvig.com/21-days.html Teach Yourself Programming in Ten Years]
+
\end{pmatrix}</math>
* Apostila adotada: [http://www.ead.cpdee.ufmg.br/cursos/C/c.html Curso de Linguagem C - Engenharia Elétrica -  UFMG]
+
 
* Ver [http://www.sj.ifsc.edu.br/~msobral/SOP/slides/aula15.pdf transparências]
+
... e o vetor ''v'' do exemplo:
* Alguns textos escritos por mim sobre  tópicos específicos da linguagem  C:
 
** [[SOP-strings|Strings]]
 
** [[SOP-funcoes|Funções]]
 
** [[SOP-stdio|Entrada e saída padrão]]
 
** [[SOP-arquivos|Arquivos]]
 
** [[SOP-struct|Estruturas de dados]]
 
  
Obs: durante as aulas usaremos o [http://www.netbeans.org NetBeans], um Ambiente Integrado de Desenvolvimento (''IDE - Integrated Development Environment''). Um IDE é um programa que auxilia o programador. Ele integra um  editor de programas, um gerenciador de projetos, compilador e um depurador (''debugger'').
+
<math>v = \begin{pmatrix}
 +
v_{1} & v_{2} & v_{3} & v_{4} & v_{5}
 +
\end{pmatrix}</math>
  
'''''Para instalar o Netbeans:'''''
+
Nas linguagens de programação em geral existe um conceito muito parecido, chamado de variáveis multidimensionais ou simplesmente ''matrizes'' (''arrays'' em inglês). Para exemplificar, no Portugol se poderiam definir a matriz ''A'' e o vetor ''v'':
# Faça o [http://netbeans.c3sl.ufpr.br/6.8/bundles/netbeans-6.8-ml-cpp-linux.sh download do instalador]. Salve-o em algum subdiretório.
 
# Abrindo um terminal, entre no subdiretório onde está o instalador e execute esse comando: <syntaxhighlight lang=bash>
 
bash netbeans-6.8-ml-cpp-linux.sh
 
</syntaxhighlight>
 
#* Caso o instalador falhe porque não encontrou a JVM (Máquina Virtual Java), instale-a com esse comando: <syntaxhighlight lang=bash>
 
sudo apt-get install -y sun-java6-jdk
 
</syntaxhighlight>
 
# Aceite as opções de instalação sugeridas pelo instalador.
 
# Ao final da instalação, o Netbeans 6.8 estará acessível pelo menu ''Aplicativos -> Programação''.
 
# Sempre que for escrever um novo programa com o Netbeans, crie um novo projeto (ver menu Arquivo->Novo Projeto). Selecione um projeto do tipo "Aplicativo C/C++".
 
  
=== Compilando o primeiro programa ===
+
<syntaxhighlight lang=text>
* O clássico ''Hello World!''
+
inicio
<syntaxhighlight lang=c n>
+
  inteiro A[2][2] <- {{1, 6}, {3, 5}}
#include <stdio.h>
+
  inteiro v[5] <- {1, 6, 2, 18, 5}
 +
 
 +
  escrever "Valor de A[0][0]: ", A[0][0], "\n"
 +
  escrever "Valor de A[0][1]: ", A[0][1], "\n"
 +
  escrever "Valor de A[1][0]: ", A[1][0], "\n"
 +
  escrever "Valor de A[1][1]: ", A[1][1], "\n"
 +
 
 +
  escrever "Valor de v[0]: ", v[0], "\n"
 +
  escrever "Valor de v[1]: ", v[1], "\n"
 +
  escrever "Valor de v[2]: ", v[2], "\n"
 +
  escrever "Valor de v[3]: ", v[3], "\n"
 +
  escrever "Valor de v[4]: ", v[4], "\n"
  
int main(int argc, char *argv[])
+
fim
{
 
printf("Alô mundo!\n");
 
}
 
 
</syntaxhighlight>
 
</syntaxhighlight>
  
* Mostrando mensagens de na tela: [http://manpages.ubuntu.com/manpages/karmic/en/man3/puts.3.html puts] e [http://manpages.ubuntu.com/manpages/karmic/en/man3/printf.3.html printf]: <syntaxhighlight lang=c n>
+
A declaração da matriz se faz como uma variável comum, porém indicando-se suas dimensões:
#include <stdio.h>
 
  
int main() {
+
<syntaxhighlight lang=text>
  int n;
+
  inteiro A[2][2] <- {{1, 6}, {3, 5}}
 +
</syntaxhighlight>
  
  n = 5;
+
Veja que a matriz ''A'' foi inicializada na declaração.
 
 
  puts("Demonstração de puts e printf");
 
  
  printf("Valor de n: %d\n", n);
+
O acesso aos elementos da matriz se faz usando-se ''índices'', que funcionam como coordenadas dos elementos que se quer acessar. Os índices iniciam em ''0'':
  
  n = n + 1;
+
<syntaxhighlight lang=text>
 
+
  # índice 0,0
   printf("Novo valor de n: %d\n", n);
+
   escrever "Valor de A[0][0]: ", A[0][0], "\n"
 
 
  return 0;
 
}
 
 
</syntaxhighlight>
 
</syntaxhighlight>
* Lendo dados do teclado: [http://manpages.ubuntu.com/manpages/karmic/en/man3/scanf.3.html scanf]<syntaxhighlight lang=c n>
 
#include <stdio.h>
 
  
int main() {
+
O exemplo acima pode ser reescrito usando-se estruturas de repetição:
  int n;
 
  
   printf("Digite um número inteiro: ");
+
<syntaxhighlight lang=text>
 +
inicio
 +
   inteiro A[2][2] <- {{1, 6}, {3, 5}}
 +
  inteiro v[5] <- {1, 6, 2, 18, 5}
 +
  inteiro i, j
  
   scanf("%d", &n);
+
   enquanto i < 2 faz
 
+
    j <- 0
   printf("Valor digitado foi %d\n", n);
+
    enquanto j < 2 faz
 +
      escrever "Valor do elemento de A na posição ", i, ", ", j, ": ", A[i][j], "\n"
 +
      j <- j + 1
 +
    fimenquanto
 +
    i <- i + 1
 +
   fimenquanto
  
   return 0;
+
   i <- 0
}
+
  enquanto i < 5 faz
 +
    escrever "valor de v na posição ", i, ": ", v[i], "\n"
 +
    i <- i + 1
 +
  fimenquanto
 +
 
 +
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
** Outras formas de ler do teclado: [http://manpages.ubuntu.com/manpages/karmic/man3/fgets.3.html getchar],  [http://manpages.ubuntu.com/manpages/karmic/en/man3/fgets.3.html fgets]
 
  
==== Tipos de dados ====
+
Como se vê, matrizes e vetores casam perfeitamente com estruturas de repetição, e são úteis para a resolução de inúmeros problemas. Por exemplo, o problema de mostrar o nome do mês a partir do número do mês, feito anteriormente com ''escolhe ... caso'' pode ser feito assim com um vetor:
{| border="1" cellpadding="2"
+
 
!Portugol
+
<syntaxhighlight lang=text>
!C
+
inicio
!Exemplo
+
  texto nome_mes[12] <- {"Janeiro", "Fevereiro", "Março", "Abril", "Maio", "Junho",
|-
+
                        "Julho", "Agosto", "Setembro", "Outubro", "Novembro",
|inteiro||int|| int x;
+
                        "Dezembro"}
|-
+
  inteiro dia, mes, ano
|caracter||char|| char letra;
 
|-
 
|real||float ou double|| float pi = 3.1416;
 
|-
 
|texto||char * ou vetor de char || char * mensagem = "Hello world";<br>char palavra[16];
 
|-
 
|logico||qualquer tipo (valor 0 = Falso, qualquer outro valor = Verdadeiro)||int ok = 1;<br>char teste = 0;
 
|}
 
  
 +
  escrever "Dia: "
 +
  ler dia
 +
  escrever "Mes: "
 +
  ler mes
 +
  escrever "Ano: "
 +
  ler ano
  
==== Comandos/funções e Estruturas de controle ====
+
  escrever dia, " de ", nome_mes[mes - 1], " de ", ano
{| border="1" cellpadding="2"
+
fim
!Portugol
+
</syntaxhighlight>
!C
 
!Exemplo
 
|-
 
|<syntaxhighlight lang=text>inteiro n, m
 
  
escrever "Ola, mundo!\n"
+
Outro problema comum é precisar guardar um conjunto de valores, e depois ordená-los:
escrever "valor de n: ", n, "\n"
 
escrever "valor de n: ", n, ", e valor de x: ", x, "\n"
 
</syntaxhighlight>||<syntaxhighlight lang=c>int n, m;
 
  
printf("Ola, mundo!\n");
+
<syntaxhighlight lang=text>
printf("valor de n: %d\n", n);
+
inicio
printf("valor de n: %d, e valor de x: %d\n", n, x);</syntaxhighlight>||
+
  inteiro v[10]
|-
+
  inteiro i
|<syntaxhighlight lang=text>inteiro n
+
  inteiro quantidade
 +
 
 +
  escrever "Quantos valores serão digitados (máximo = 10) ? "
 +
  ler quantidade
 +
 
 +
  i <- 0
 +
  enquanto i < quantidade faz
 +
    escrever "valor ", i, ": "
 +
    ler v[i]
 +
    i <- i + 1
 +
  fimenquanto
  
ler n</syntaxhighlight>||<syntaxhighlight lang=c>int n;
+
  // ordena os valores ...
  
scanf("%d", &n);</syntaxhighlight>||
+
  escrever "valores ordenados: "
|-
+
  i <- 0
|<syntaxhighlight lang=text>se condição então
+
  enquanto i < quantidade
//comandos
+
    escrever v[i], " "
fimse</syntaxhighlight> ||<syntaxhighlight lang=c>if (condição) {
+
    i <- i + 1
//comandos
+
   fimenquanto
}</syntaxhighlight>||
+
fim
|-
+
</syntaxhighlight>
|<syntaxhighlight lang=text>se condição então
+
 
   //comandos
+
=== Atividades ===
senão
+
 
  //comandos
+
# Escreva um algoritmo que leia 5 números do teclado, e depois mostre-os em ordem inversa à que foi digitada.
fimse</syntaxhighlight> ||<syntaxhighlight lang=c>if (condição) {
+
# Escreva um algoritmo que leia dois vetores de 5 números, e depois mostre se os vetores são iguais.
//comandos
+
# Escreva um algoritmo que leia um palavra do teclado e depois procure-a numa lista de palavras preexistente. Essa lista deve ser implementada usando um vetor.
} else {
+
# Escreva um algoritmo que leia 5 números, e mostre-os em ordem crescente.
//comandos
+
# Modifique o algoritmo anterior para mostrá-los em ordem decrescente.
}</syntaxhighlight> ||
+
# Em um jogo de bingo devem-se contar quantos números de uma aposta foram sorteados no bingo. Faça um algoritmo que, dados os números sorteados e uma aposta, conta quantos números apostados foram sorteados.
|-
+
 
|<syntaxhighlight lang=text>escolhe expressão
+
== 12/05: Estruturas de repetição ==
  caso valor1: 
 
    //comandos
 
  caso valor2:
 
    //comandos
 
  defeito:
 
    //comandos
 
fimescolhe</syntaxhighlight>||<syntaxhighlight lang=c>switch (expressão) {
 
  case valor1:
 
    //comandos
 
  case valor2:
 
    //comandos
 
  default:
 
    //comandos
 
}</syntaxhighlight>||
 
  |-
 
|<syntaxhighlight lang=text>enquanto condição faz
 
//comandos
 
fimenquanto</syntaxhighlight>||<syntaxhighlight lang=c>while (condição) {
 
  //comandos
 
}</syntaxhighlight>||
 
  |-
 
|<syntaxhighlight lang=text>para variavel de inicio ate fim passo incremento
 
//comandos
 
proximo</syntaxhighlight>||<syntaxhighlight lang=c>for (variavel=inicio; variavel <= fim; variavel++) {
 
//comandos
 
}</syntaxhighlight>||
 
|}
 
  
=== Atividades ===
+
=== Para ''variavel'' de ''inicio'' ate ''fim'' passo ''incremento'' ===
  
* Traduza para C os seguintes algoritmos Portugol:  
+
Há casos em que se deseja repetir uma parte de um algoritmo certo número de vezes. Para esses casos há uma estrutura mais prática que ''enquanto condição faz'':
*# <syntaxhighlight lang=text>
+
 
Inicio
+
<syntaxhighlight lang=text>
   inteiro x, y
+
inicio
+
  inteiro i
   Escrever "Digite um numero: ",
+
   inteiro v[5]
   Ler x
+
 
   Escrever "Digite outro numero: ",
+
   escrever "Digite 5 números: \n"
   Ler y
+
 
  Escrever "Soma = ", x+y
+
  para i de 0 ate 4 passo 1
Fim
+
    escrever "Numero ", i, ": "
 +
    ler v[i]
 +
   proximo
 +
 
 +
   escrever "\nOs numeros em ordem inversa são:\n\n"
 +
 
 +
   para i de 4 ate 0 passo -1
 +
    escrever "Numero ", i, ": ", v[i], "\n"
 +
  proximo
 +
 
 +
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
*# <syntaxhighlight lang=text>
+
 
Inicio
+
=== Atividades ===
  inteiro x, y, z
+
 
+
# Escreva o algoritmo para comparar dois vetores, porém usando a estrutura ''para''.
  Escrever "Digite um numero: ",
+
# Escreva um algoritmo para procurar se um vetor menor (com menos valores) está contido em um vetor maior. Caso afirmativo, mostre a partir de que posição ele aparece. Assuma vetores de números inteiros.
  Ler x
+
# Modifique o algoritmo acima para mostrar todas as ocorrências do vetor menor dentro do maior.
  Escrever "Digite outro numero: ",
+
# Modifique o algoritmo do anterior para remover todas as ocorrências do vetor menor dentro do maior.
  Ler y
+
# Resolva o problema do bingo usando a estrutura ''para''
  z <- x + y
+
 
  Escrever "Soma = ", z
+
== 18/05: Revisão ==
Fim
+
 
</syntaxhighlight>
+
...exercícios
*# <syntaxhighlight lang=text>
+
 
Inicio
+
Resolver a avaliação de 2010-2:
  Inteiro n1, n2, n3, r
+
 
+
1) '''Contador de moedas:''' faça um programa que leia valores de moedas e some as quantidades de tipos de moedas informadas. Por exemplo, se o usuário digitar 25, 50, 25, 5, 10, 5, o programa deve informar: ''2 moedas de 5 centavos, 1 moeda de 10 centavos, 2 moedas de 25 centavos, 1 moeda de 50 centavos''. São aceitos apenas  valores de moedas de 1, 5, 10, 25 e 50 centavos.  Seu programa deve ler 10 valores de moedas, e então apresentar o resultado.
  Escrever "Primeiro numero: "
+
 
  ler n1
+
2) '''Calculadora de troco:''' escreva um programa que calcule o troco a ser devolvido a um cliente. O troco deve ser composto de notas de 50, 20, 10, 5, 2 ou 1 real, e também moedas de 1, 5, 10, 25 ou 50 centavos. Dê preferência ao uso de notas e moedas de maior valor. Por exemplo, se o troco a ser devolvido for ''R$ 17,75'', seu programa deve informar ''1 nota de R$ 10, 1 nota de R$ 5, 1 nota de R$ 2, 1 moeda de R$ 0,50, 1 moeda de R$ 0,25''.
  Escrever "Segundo numero: "
+
 
  ler n2
+
3) '''Modificação de senha:''' Para modificar uma senha deve-se primeiro fornecer a senha
  Escrever "Terceiro numero: "
+
atual, e então a nova senha.  É necessário escrever duas vezes a nova
  ler n3
+
senha para confirmá-la. Escreva um  algoritmo  que modifique uma senha
+
predefinida (no seu programa ela pode estar guardada em uma variável), seguindo essa regra de mudança de senha.
  r <- (n1 + n2 + n3) /3
+
 
+
4) '''Nota de uma prova olímpica:''' um atleta de saltos ornamentais tem seu salto avaliado por 6 juízes. Após descartar a maior e a menor nota, calcula-se a média aritmética das notas dadas. Faça um programa que calcule a nota de um  atleta.
  Escrever "Media=", r
+
 
Fim
+
... mais algumas questões interessantes:
 +
 
 +
5) '''Filtro:''' Um programa possui 10 números inteiros em um vetor. No entanto, para a próxima etapa de processamento apenas os números entre 3 e 8 são válidos. Escreva um algoritmo que remova os números inválidos do vetor. Ao final o vetor deve conter somente os números válidos.
 +
 
 +
6) '''Tabuleiro:''' Escreva um programa que mostre o conteúdo de uma matriz 4 x 4 na tela. Essa matriz contém valores inteiros que podem ser positivos ou negativos. Ao mostrar cada valor da matriz, deve-se seguir a seguinte regra:
 +
* Valor negativo: deve ser mostrado um espaço em branco
 +
* Valor entre 1 e 8: mostrar o próprio valor
 +
* Valor acima de 8: mostrar o caractere '''H'''
 +
 
 +
Além disso, a matriz deve ser mostrada com uma grade. Por exemplo, a matriz com conteúdo:
 +
 
 +
<math>A = \begin{pmatrix}
 +
1 & 6 & 10 & -1 \\
 +
3 & 5 & -1 & -1 \\
 +
10 & 4 & -1 & 5 \\
 +
3 & -1 & 1 & -1 \\
 +
\end{pmatrix}</math>
 +
 
 +
... que em Portugol seria declarada assim:
 +
 
 +
<syntaxhighlight lang=text>
 +
inteiro A <- {{1, 6, 10, -1}, {3, 5, -1, -1},  
 +
              {10, 4, -1, 5}, {3, -1, 1, -1}}
 
</syntaxhighlight>
 
</syntaxhighlight>
*# <syntaxhighlight lang=text>
+
 
Inicio
+
... deveria ser mostrada da seguinte forma:
   inteiro anos, dias
+
 
+
<syntaxhighlight lang=text>
   Escrever "Quantos anos se passaram ? "
+
 
   Ler anos
+
..| 1 | 2 | 3 | 4 |
  dias <- anos * 365
+
-------------------
   Escrever "... então se passaram ", dias, " dias"
+
A | 1 | 6 | H |   |
Fim
+
-------------------
 +
B | 3 | 5 |  |   |
 +
-------------------
 +
C | H | 4 |   | 5 |
 +
-------------------
 +
D | 3 |   | 1 |  |
 +
-------------------
 
</syntaxhighlight>
 
</syntaxhighlight>
*# <syntaxhighlight lang=text>
+
 
Inicio
+
Quer dizer, as colunas devem ser identificadas por seus números, e as linhas devem ser identificadas pelas letras '''A''', '''B''','''C''', '''D'''.
  constante inteiro diasPorAno <- 365
+
 
  inteiro anos, dias
+
= Linguagem C: Projeto final =
   
+
 
  Escrever "Quantos anos se passaram ? "
+
== 19/05:  Introdução à linguagem C ==
  Ler anos
+
 
  dias <- anos * diasPorAno
+
* Baseado no [[Guia Básico de C]].
  Escrever "... então se passaram ", dias, " dias"
+
* Para provocar: [http://norvig.com/21-days.html Teach Yourself Programming in Ten Years]
Fim
+
* Apostila adotada: [http://www.ead.cpdee.ufmg.br/cursos/C/c.html Curso de Linguagem C - Engenharia Elétrica - UFMG]
 +
* Ver [http://www.sj.ifsc.edu.br/~msobral/SOP/slides/aula15.pdf transparências]
 +
* Alguns textos escritos por mim sobre  tópicos específicos da linguagem C:
 +
** [[SOP-strings|Strings]]
 +
** [[SOP-funcoes|Funções]]
 +
** [[SOP-stdio|Entrada e saída padrão]]
 +
** [[SOP-arquivos|Arquivos]]
 +
** [[SOP-struct|Estruturas de dados]]
 +
 
 +
Obs: durante as aulas usaremos o [http://www.netbeans.org NetBeans], um Ambiente Integrado de Desenvolvimento (''IDE - Integrated Development Environment''). Um IDE é um programa que auxilia o programador. Ele integra um  editor de programas, um gerenciador de projetos, compilador e um depurador (''debugger'').
 +
 
 +
'''''Para instalar o Netbeans:'''''
 +
# Faça o [http://netbeans.c3sl.ufpr.br/6.8/bundles/netbeans-6.8-ml-cpp-linux.sh download do instalador]. Salve-o em algum subdiretório.
 +
# Abrindo um terminal, entre no subdiretório onde está o instalador e execute esse comando: <syntaxhighlight lang=bash>
 +
bash netbeans-6.8-ml-cpp-linux.sh
 +
</syntaxhighlight>
 +
#* Caso o instalador falhe porque não encontrou a JVM (Máquina Virtual Java), instale-a com esse comando: <syntaxhighlight lang=bash>
 +
sudo apt-get install -y sun-java6-jdk
 
</syntaxhighlight>
 
</syntaxhighlight>
*# <syntaxhighlight lang=text>
+
# Aceite as opções de instalação sugeridas pelo instalador.
inicio
+
# Ao final da instalação, o Netbeans 6.8 estará acessível pelo menu ''Aplicativos -> Programação''.
  real massa
+
# Sempre que for escrever um novo programa com o Netbeans, crie um novo projeto (ver menu Arquivo->Novo Projeto). Selecione um projeto do tipo "Aplicativo C/C++".
  real forca
+
 
  real aceleracao
+
=== Compilando o primeiro programa ===
  constante real g <- 9.8
+
 
  constante real ac <- 0.01
+
Obs: para compilar um programa você deve salvá-lo em um arquivo com extensão '''.c'''. Por exemplo, ao editar o exemplo abaixo, você pode gravá-lo no arquivo ''hello.c''. Em seguida você deve compilá-lo usando o seguinte comando:
 
+
 
  escrever "força: "
+
<syntaxhighlight lang=bash>
  ler forca
+
gcc hello.c -o hello
 
+
</syntaxhighlight>
  escrever "massa: "
+
 
  ler massa
+
Para executá-lo, faça assim:
 
+
 
  aceleracao <- forca/massa - ac*massa*g
+
<syntaxhighlight lang=bash>
 
+
./hello
  escrever "aceleracao=", aceleracao, " m/s2"
 
 
 
fim
 
 
</syntaxhighlight>
 
</syntaxhighlight>
*# <syntaxhighlight lang=text>
+
 
inicio
+
O arquivo que contém o programa em linguagem C se chama ''arquivo de código-fonte''. O arquivo que contém o programa compilado se chama ''arquivo de código-objeto''.
  real a, b, c
+
 
  real delta
+
 
  real x1, x2
+
* O clássico ''Hello World!''
 
+
<syntaxhighlight lang=c>
  escrever "Forneça os coeficientes da equação de 2o grau (formato: ax^2 + bx + c):\n"
+
#include <stdio.h>
  escrever "a="
+
 
  ler a
+
int main(int argc, char *argv[])
   escrever "b="
+
{
  ler b
+
printf("Alô mundo!\n");
   escrever "c="
+
}
  ler c
+
</syntaxhighlight>
 +
 
 +
* Mostrando mensagens de na tela: [http://manpages.ubuntu.com/manpages/karmic/en/man3/puts.3.html puts] e [http://manpages.ubuntu.com/manpages/karmic/en/man3/printf.3.html printf]: <syntaxhighlight lang=c>
 +
#include <stdio.h>
 +
 
 +
int main() {
 +
   int n;
 +
 
 +
   n = 5;
 
    
 
    
   delta <- b^2 - 4*a*c
+
   puts("Demonstração de puts e printf");
  x1 <- (-b + delta^0.5)/(2*a)
+
 
   x2 <- (-b - delta^0.5)/(2*a)
+
   printf("Valor de n: %d\n", n);
 
+
 
   escrever "1a raiz=", x1
+
   n = n + 1;
   escrever "\n2a raiz=", x2 
+
 
fim
+
   printf("Novo valor de n: %d\n", n);
</syntaxhighlight>
+
 
*# <syntaxhighlight lang=text>
+
  return 0;
inicio
+
}
      real x1, x2, x3, x4, x5
 
      real media
 
      real desvioPadrao
 
      constante inteiro N <- 5
 
     
 
      // Ler os cinco valores pelo teclado
 
      ler x1
 
      ler x2
 
      ler x3
 
      ler x4
 
      ler x5
 
     
 
      // Calcular a media
 
      media <- (x1 + x2 + x3 + x4 + x5) / N
 
     
 
      // Calcular o desvio padrao
 
      desvioPadrao <- (x1 - media)^2 + (x2 - media)^2 + (x3 - media)^2 + (x4 - media)^2 + (x5 - media)^2
 
      desvioPadrao <- (desvioPadrao / (N-1))^0.5
 
     
 
      escrever "Media=", media
 
      escrever "\nDesvio padrao=", desvioPadrao
 
fim
 
 
</syntaxhighlight>
 
</syntaxhighlight>
*# <syntaxhighlight lang=text>
+
* Lendo dados do teclado: [http://manpages.ubuntu.com/manpages/karmic/en/man3/scanf.3.html scanf]<syntaxhighlight lang=c>
inicio
+
#include <stdio.h>
      real renda
 
      real irpf
 
     
 
      escrever "Informe sua renda: "
 
      ler renda
 
     
 
      se renda < 1372.81 entao
 
        irpf <- 0
 
      senao
 
        se renda < 2743.25 entao
 
          irpf <- (renda - 205.92)*0.15
 
        senao
 
          irpf <- (renda - 548.82)*0.275
 
        fimSe
 
      fimSe
 
     
 
      escrever "Imposto devido: ", irpf 
 
fim
 
</syntaxhighlight>
 
*# <syntaxhighlight lang=text>
 
inicio
 
    inteiro dividendo
 
    inteiro divisor
 
    inteiro resto , quociente
 
  
    escrever "Dividendo: "
+
int main() {
    ler dividendo
+
  int n;
    escrever "Divisor: "
 
    ler divisor
 
  
    se divisor = 0 entao
+
  printf("Digite um número inteiro: ");
        escrever "Nao pode dividir: divisor = 0 !!!"
 
    senao
 
        resto <- dividendo % divisor
 
        se resto = 0 entao
 
            quociente <- dividendo / divisor
 
            escrever dividendo , " / " , divisor , " = " , quociente
 
        senao
 
            escrever "Nao pode fazer divisao inteira"
 
            escrever " (resto = " , resto , ")"
 
        fimse
 
    fimse
 
fim
 
</syntaxhighlight>
 
*# <syntaxhighlight lang=text>
 
inicio
 
    inteiro termometro , barometro , tempo
 
  
    escrever "Qual a condição do termômetro: \n"
+
  scanf("%d", &n);
    escrever "Digite 1 para baixando , 2 para estacionário e 3 para subindo. \n"
 
    ler termometro
 
  
    escrever "Informe a condição do barômetro: \n"
+
  printf("Valor digitado foi %d\n", n);
    escrever "Digite 1 para baixando , 2 para estacionário e 3 para subindo. \n"
 
    ler barometro
 
  
    tempo <- termometro*10 + barometro
+
  return 0;
 +
}
 +
</syntaxhighlight>
 +
** Outras formas de ler do teclado: [http://manpages.ubuntu.com/manpages/karmic/man3/fgets.3.html getchar],  [http://manpages.ubuntu.com/manpages/karmic/en/man3/fgets.3.html fgets]
  
    escolhe tempo
+
==== Tipos de dados ====
        caso 11:
+
{| border="1" cellpadding="2"
            escrever "Chuvas abundantes e ventos de sul a sudoeste fortes"
+
!Portugol
        caso 12:
+
!C
            escrever "Chuva Provavel , ventos de sul a sudeste"
+
!Exemplo
        caso 13:
+
|-
            escrever "Tempos Bons , ventos de sul a sudeste"
+
|inteiro||int|| int x;
        caso 21:
+
|-
            escrever "Frente quente com chuva provavel"
+
|caracter||char|| char letra;
        caso 22:
+
|-
            escrever "Tempo Incerto , ventos variaveis"
+
|real||float ou double|| float pi = 3.1416;
        caso 23:
+
|-
            escrever "Tempos Bons , ventos do leste frescos"
+
|texto||char * ou vetor de char || char * mensagem = "Hello world";<br>char palavra[16];
        caso 31:
+
|-
            escrever " Tempo instavel , aproximaçao de frente"
+
|logico||qualquer tipo (valor 0 = Falso, qualquer outro valor = Verdadeiro)||int ok = 1;<br>char teste = 0;
        caso 32:
+
|}
            escrever "Tempo Mudando para bom , ventos de leste"
+
 
        caso 33:
+
 
            escrever "Tempos Bons , ventos quentes e secos"
+
==== Comandos/funções e Estruturas de controle ====
        defeito:
+
{| border="1" cellpadding="2"
            escrever "Utilize somente os algorismos de 1 a 3 para indicar as condiçoes do equipamentos"
+
!Portugol
    fimescolhe
+
!C
fim
+
!Exemplo
</syntaxhighlight>
+
|-
*# <syntaxhighlight lang=text>
+
|<syntaxhighlight lang=text>inteiro n, m
inicio
+
 
    // coeficientes do polinomio  [ax^2 + bx + c = 0 ]
+
escrever "Ola, mundo!\n"
    real a , b , c
+
escrever "valor de n: ", n, "\n"
   
+
escrever "valor de n: ", n, ", e valor de x: ", x, "\n"
    escrever "Forneça os coeficientes da equação de 2o grau:\n"
+
</syntaxhighlight>||<syntaxhighlight lang=c>int n, m;
    escrever "a="
+
 
    ler a
+
printf("Ola, mundo!\n");
    escrever "b="
+
printf("valor de n: %d\n", n);
    ler b
+
printf("valor de n: %d, e valor de x: %d\n", n, x);</syntaxhighlight>||
    escrever "c="
+
|-
    ler c
+
|<syntaxhighlight lang=text>inteiro n
   
+
 
    // equação do tipo [ bx + c = 0 ]
+
ler n</syntaxhighlight>||<syntaxhighlight lang=c>int n;
    se a = 0 entao
+
 
        escrever " não é uma equação de 2o grau !!!"
+
scanf("%d", &n);</syntaxhighlight>||
    senao
+
|-
        // calcular o delta => interior da raiz
+
|<syntaxhighlight lang=text>se condição então
        real delta
+
//comandos
       
+
fimse</syntaxhighlight> ||<syntaxhighlight lang=c>if (condição) {
        delta <- b ^ 2 - 4 * a * c
+
//comandos
       
+
}</syntaxhighlight>||
        // não existem raizes  reais de números negativos
+
|-
        se delta < 0 entao
+
|<syntaxhighlight lang=text>se condição então
            escrever " não tem raizes reais"
+
  //comandos
        senao
+
senão
            // -----------  raiz dupla ----------------
+
  //comandos
            se delta = 0 entao
+
fimse</syntaxhighlight> ||<syntaxhighlight lang=c>if (condição) {
                real x1
+
//comandos
                x1 <- -b / 2 * a
+
} else {
                escrever "\nraiz dupla : " , x1
+
//comandos
            senao
+
}</syntaxhighlight> ||
                // - ---------- duas raizes ---------------
+
  |-  
                real x1 , x2
+
|<syntaxhighlight lang=text>escolhe expressão
                x1 <- ( -b + raiz ( delta ) ) / 2 * a
+
  caso valor1: 
                x2 <- ( -b - raiz ( delta ) ) / 2 * a
+
    //comandos
                escrever "\nraiz x1 : " , x1
+
  caso valor2:
                escrever "\nraiz x2 : " , x2
+
    //comandos
            fimse//raiz dupla
+
  defeito:
        fimse// delta >0
+
    //comandos
    fimse// a <> 0
+
fimescolhe</syntaxhighlight>||<syntaxhighlight lang=c>switch (expressão) {
fim
+
  case valor1:
</syntaxhighlight>
+
    //comandos
*# <syntaxhighlight lang=text>
+
  case valor2:
inicio
+
    //comandos
    inteiro num, bit
+
  default:
    inteiro base
+
    //comandos
   
+
}</syntaxhighlight>||
    escrever "Este algoritmo converte um número inteiro para sua representação binária.\n"
+
|-
    Escrever "O número deve estar entre 0 e 131071, e a representação binária\n"
+
|<syntaxhighlight lang=text>enquanto condição faz
    escrever "terá 17 bits\n\n"
+
//comandos
    escrever "Digite o numero a ser convertido para binário: "
+
fimenquanto</syntaxhighlight>||<syntaxhighlight lang=c>while (condição) {
    ler num
+
  //comandos
 +
}</syntaxhighlight>||
 +
|-
 +
|<syntaxhighlight lang=text>para variavel de inicio ate fim passo incremento
 +
//comandos
 +
proximo</syntaxhighlight>||<syntaxhighlight lang=c>for (variavel=inicio; variavel <= fim; variavel++) {
 +
//comandos
 +
}</syntaxhighlight>||
 +
|}
 +
 
 +
=== Atividades ===
  
    base <- 65536
+
* Traduza para C os seguintes algoritmos Portugol:
    enquanto base > 0 faz
 
        bit <- ( num / base ) % 2
 
        escrever bit, " "
 
        base <- base / 2
 
    fimenquanto
 
fim
 
</syntaxhighlight>
 
 
*# <syntaxhighlight lang=text>
 
*# <syntaxhighlight lang=text>
inicio
+
Inicio
    inteiro n , fat
+
  inteiro x, y
    ler n
+
    fat <- 1
+
  Escrever "Digite um numero: ",
    enquanto n > 1 faz
+
  Ler x
      fat <- fat * n
+
  Escrever "Digite outro numero: ",
      n <- n - 1       
+
  Ler y
    fimenquanto
+
  Escrever "Soma = ", x+y
   
+
Fim
    escrever "Fatorial=" , fat
 
fim
 
 
</syntaxhighlight>
 
</syntaxhighlight>
 
*# <syntaxhighlight lang=text>
 
*# <syntaxhighlight lang=text>
inicio
+
Inicio
    inteiro valor , menor , contador
+
  inteiro x, y, z
    ler menor
+
    contador <- 9
+
  Escrever "Digite um numero: ",
    enquanto contador > 0 faz
+
  Ler x
        ler valor
+
  Escrever "Digite outro numero: ",
        se valor < menor entao
+
  Ler y
            menor <- valor
+
  z <- x + y
        fimse
+
  Escrever "Soma = ", z
        contador <- contador - 1
+
Fim
    fimenquanto
 
    escrever "menor valor = ", menor
 
fim
 
 
</syntaxhighlight>
 
</syntaxhighlight>
 
*# <syntaxhighlight lang=text>
 
*# <syntaxhighlight lang=text>
inicio
+
Inicio
    inteiro numero , n , resto <- 1
+
  Inteiro n1, n2, n3, r
    escrever "Forneçaa um número: "
+
    ler numero
+
  Escrever "Primeiro numero: "
    n <- 2
+
  ler n1
    enquanto n <= numero / 2 e resto =/= 0 faz
+
  Escrever "Segundo numero: "
        resto <- numero % n
+
  ler n2
        escrever "n=" , n , ": resto=" , resto , "\n"
+
  Escrever "Terceiro numero: "
        n <- n + 1
+
  ler n3
    fimenquanto
+
   
+
  r <- (n1 + n2 + n3) /3
    se resto = 0 entao
+
        escrever "nao primo: divisivel por " , n - 1
+
  Escrever "Media=", r
    senao
+
Fim
        escrever "primo"
+
</syntaxhighlight>
    fimse
+
*# <syntaxhighlight lang=text>
fim
+
Inicio
 +
  inteiro anos, dias
 +
 +
  Escrever "Quantos anos se passaram ? "
 +
  Ler anos
 +
  dias <- anos * 365
 +
  Escrever "... então se passaram ", dias, " dias"
 +
Fim
 
</syntaxhighlight>
 
</syntaxhighlight>
 
*# <syntaxhighlight lang=text>
 
*# <syntaxhighlight lang=text>
// Le 5 valores e identifica os dois maiores.
+
Inicio
inicio
+
  constante inteiro diasPorAno <- 365
    inteiro valor , maior1 , maior2 , contador
+
  inteiro anos, dias
   
+
    ler valor
+
  Escrever "Quantos anos se passaram ? "
    maior1 <- valor
+
  Ler anos
   
+
  dias <- anos * diasPorAno
    ler valor
+
  Escrever "... então se passaram ", dias, " dias"
    se valor > maior1 entao
+
Fim
      maior2 <- maior1
+
</syntaxhighlight>
      maior1 <- valor
+
*# <syntaxhighlight lang=text>
    senao
+
inicio
      maior2 <- valor
+
  real massa
    fimse
+
  real forca
 
+
  real aceleracao
    contador <- 3
+
  constante real g <- 9.8
    enquanto contador > 0 faz
+
  constante real ac <- 0.01
        ler valor
+
 
        se valor > maior1 entao
+
  escrever "força: "
            maior2 <- maior1
+
  ler forca
            maior1 <- valor
+
 
        senao
+
  escrever "massa: "
            se valor > maior2 entao
+
  ler massa
                maior2 <- valor
+
 
            fimse
+
  aceleracao <- forca/massa - ac*massa*g
        fimse
+
 
        contador <- contador - 1
+
  escrever "aceleracao=", aceleracao, " m/s2"
    fimenquanto
+
 
 
 
    escrever "maior valor = " , maior1
 
    escrever "\nsegundo maior valor = " , maior2
 
 
fim
 
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
 
+
*# <syntaxhighlight lang=text>
== 08/11: Começo do projeto ==
+
inicio
 
+
  real a, b, c
Para referência: [http://www.ead.cpdee.ufmg.br/cursos/C/c.html apostila online sobre linguagem C].
+
  real delta
 
+
  real x1, x2
=== O jogo: Campo Minado ===
+
 
 
+
  escrever "Forneça os coeficientes da equação de 2o grau (formato: ax^2 + bx + c):\n"
O [http://pt.wikipedia.org/wiki/Campo_minado ''Campo Minado''] é um jogo clássico disponível em diferentes sistemas operacionais. Basicamente devem-se procurar as minas existentes em um campo quadriculado, perdendo-se o jogo se ''pisar''  em uma mina, e vencendo se descobrir todas as minas. O jogo  oferece pistas sobre a localização das minas, e usando-se um  pouco de lógica podem-se encontrá-las. Uma  versão desse jogo para Linux aparece na figura a seguir .
+
  escrever "a="
 
+
  ler a
[[imagem:Minas-linux.png]]
+
  escrever "b="
 
+
  ler b
A cada jogada deve-se escolher uma casa do tabuleiro, optando-se por ''pisá-la'' (revelando-a) ou marcá-la como uma provável mina. Ao ''pisar'' numa casa, três ações podem ocorrer:
+
  escrever "c="
# A casa contém uma mina, o que revela  todas as demais minas e encerra o jogo com derrota.
+
  ler c
# A casa é vizinha a uma ou mais minas, e assim em seu lugar aparece o número de minas em casas vizinhas.
+
 
# Nenhuma mina existe em casas vizinhas, então a casa aparece vazia. Além disso, todas as casas vizinhas que também  não possuam minas são reveladas.
+
  delta <- b^2 - 4*a*c
 
+
  x1 <- (-b + delta^0.5)/(2*a)
Ao final do jogo, a pontuação é dada pelo tempo que se levou para se descobrirem as minas. O jogo contabiliza uma lista de melhores jogadas, contendo o nome do jogador e o tempo de jogo. Melhores jogadas são aquelas com menores tempos de jogo.
+
  x2 <- (-b - delta^0.5)/(2*a)
 
+
 
A versão do jogo a ser desenvolvida será baseada em texto ''(mas quem quiser fazer uma versão gráfica fique à vontade !)''. Basicamente  deve ser apresentado o tabuleiro, mostrando-se apenas as casas já reveladas e o tempo de jogo decorrido, e um ''prompt'' pedindo as coordenadas da próxima casa assim como o tipo de ação (se ''pisar'' na casa ou marcar a provável existência de uma mina).
+
  escrever "1a raiz=", x1
 
+
  escrever "\n2a raiz=", x2 
=== Etapas de desenvolvimento ===
+
fim
 
 
* Proposta de código que contempla:
 
** Bibliotecas e definições
 
** Declaração de constantes e variáveis
 
*** Uso de variáveis com mesmo nome e diferentes escopos
 
*** Vetor e matriz
 
** Operadores lógicos e matemáticos
 
** Expressões
 
*** E/S
 
*** Estruturas de decisão e repetição
 
** Funções
 
*** Passagem de parâmetro por valor e por referência
 
** Acesso a uma matriz através de um vetor linear (função <tt>iniciaJogo</tt>)
 
** Ponteiros
 
 
 
=== O laço principal do jogo ... ===
 
 
 
O jogo funciona com um laço principal, que lê as coordenadas da pŕoxima casa e a ação a ser feita, e atualiza o tabuleiro apropriadamente:
 
 
 
[[imagem:Fluxo-Campo-Minado.png|400px]]
 
 
 
Note que nesse laço devem-se contabilizar quantas minas fora descobertas. Esse valor é necessário para decidir se o jogo já acabou.
 
 
 
=== O tabuleiro ===
 
 
 
Representar o tabuleiro: etapas X a Y.
 
 
 
O tabuleiro do campo minado deve ser representado em formato de texto conforme a figura abaixo. Nesta figura, o tabuleiro está completamente revelado.
 
 
 
 
 
[[imagem:Tabuleiro-Minado.png]]
 
 
 
 
 
As colunas são identificadas por letras maiúsculas, e as linhas por números. Cada casa do tabuleiro pode conter uma mina ou um número que conta quantas minas existem em casas vizinhas. Casas já reveladas devem mostrar essa contagem de minas vizinhas, sendo que se não houver  minas a casa deve ser mostrada vazia (preenchida com espaço). Casa em  que se marcou a existência de uma mina deve mostrar a letra '''M'''. Por fim, casas ainda não reveladas devem ser preenchidas com o caractere '''?'''. Um tabuleiro parcialmente revelado apareceria como a figura abaixo.
 
 
 
 
 
[[imagem:Tabuleiro-Minado2.png]]
 
 
 
 
 
==== Etapa 1: Modelando  o tabuleiro ====
 
 
 
Conteúdos abordados:
 
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c300.html declaração de variáveis]
 
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c940.html saída de dados na tela]
 
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c500.html Matrizes]
 
 
 
Deve-se nessa etapa escolher uma forma de representar o tabuleiro dentro do programa. Devem-se pensar também  em como representar as casas do campo minado:
 
* Como definir que uma casa possui uma mina ?
 
* Como definir que uma casa está  vazia ? Nesse caso, como informar a quantidade de minas em casas vizinhas ?
 
* Como definir se uma casa já foi pisada ?
 
 
 
Ponto de partida para mostrar um tabuleiro na tela. O tabuleiro foi modelado como uma matriz de inteiros bidimensional.
 
 
 
<syntaxhighlight lang=c>
 
#include <stdio.h>
 
 
 
int main(int argc, char** argv) {
 
    int tabuleiro[5][5] = { {0,0,1,1,0}, {1,1,2,0,0}, {10,1,0,0,0},
 
                          {1,1,1,0,0}, {0,0,0,0,10} };
 
    int i, j;
 
 
 
    //i indica a linha, j a coluna
 
    i = 0;
 
    while (i < 5) {
 
        // O while abaixo mostra todas as colunas da linha "i"
 
        j = 0;
 
        while (j < 5) {
 
            printf("%d ", tabuleiro[i][j]);
 
            j++;
 
        }
 
 
 
        printf("\n");
 
        i++;
 
    }
 
 
 
    return (EXIT_SUCCESS);
 
}
 
 
</syntaxhighlight>
 
</syntaxhighlight>
 
+
*# <syntaxhighlight lang=text>
Cada casa dessa matriz contém um número inteiro. Para representar o estado de cada casa do tabuleiro sugeriu-se um código numérico:
+
inicio
* ''Casa com mina:'' algum número > 8
+
      real x1, x2, x3, x4, x5
* ''Casa sem mina:'' um número que conte quantas minas existem em casas vizinhas. Tal número estará entre 0 e 8.
+
      real media
 
+
      real desvioPadrao
 
+
      constante inteiro N <- 5
 
+
     
== 09/11: O tabuleiro ==
+
      // Ler os cinco valores pelo teclado
 
+
      ler x1
Conteúdos abordados:
+
      ler x2
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c300.html declaração de variáveis]
+
      ler x3
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c530.html matrizes de números]
+
      ler x4
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c940.html saída de dados na tela]
+
      ler x5
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c410.html estrutura de decisão: ''if'']
+
     
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c440.html estrutura de repetição: ''while'']
+
      // Calcular a media
 
+
      media <- (x1 + x2 + x3 + x4 + x5) / N
=== Desenhando o tabuleiro completo ===
+
     
 
+
      // Calcular o desvio padrao
Dando continuidade à visualização do tabuleiro, agora deve-se desenhá-lo por completo na tela. Quer dizer, mostrar um tabuleiro com 10 linhas e 10 colunas, seguindo a abordagem da [[SOP-2010-2-sobral#08.2F11:_Come.C3.A7o_do_projeto|aula anterior]].
+
      desvioPadrao <- (x1 - media)^2 + (x2 - media)^2 + (x3 - media)^2 + (x4 - media)^2 + (x5 - media)^2
 
+
      desvioPadrao <- (desvioPadrao / (N-1))^0.5
Para mostrar o tabuleiro, deve-se explorar o uso da função [[SOP-stdio|printf]], que serve para mostrar dados na tela.
+
     
 
+
      escrever "Media=", media
=== Zerando o tabuleiro ===
+
      escrever "\nDesvio padrao=", desvioPadrao
 
+
fim
Fluxograma do algoritmo que zera o tabuleiro:
 
 
 
[[imagem:Zera-tabuleiro.png|300px]]
 
 
 
 
 
... e esse fluxograma traduzido para linguagem C:
 
 
 
<syntaxhighlight lang=c>
 
    // Zerar todas as posições do tabuleiro !
 
    i = 0;
 
    while ( i < LINHAS) {
 
        j = 0;
 
        while (j < COLUNAS) {
 
            tabuleiro[i][j] = 0;
 
            j++;
 
        }
 
        i++;
 
    }
 
 
</syntaxhighlight>
 
</syntaxhighlight>
 +
*# <syntaxhighlight lang=text>
 +
inicio
 +
      real renda
 +
      real irpf
 +
     
 +
      escrever "Informe sua renda: "
 +
      ler renda
 +
     
 +
      se renda < 1372.81 entao
 +
        irpf <- 0
 +
      senao
 +
        se renda < 2743.25 entao
 +
          irpf <- (renda - 205.92)*0.15
 +
        senao
 +
          irpf <- (renda - 548.82)*0.275
 +
        fimSe
 +
      fimSe
 +
     
 +
      escrever "Imposto devido: ", irpf 
 +
fim
 +
</syntaxhighlight>
 +
*# <syntaxhighlight lang=text>
 +
inicio
 +
    inteiro dividendo
 +
    inteiro divisor
 +
    inteiro resto , quociente
  
=== Colocando as minas ===
+
    escrever "Dividendo: "
 
+
    ler dividendo
No tabuleiro devem ser colocadas 10 minas aleatoriamente. Isso significa que para cada uma dessas minas, devem-se gerar aleatoriamente  suas coordenadas no tabuleiro. A geração de números aleatórios pode ser feita usando-se a função [http://manpages.ubuntu.com/manpages/lucid/man3/random.3.html random()]. Essa função gera um número inteiro entre 0 e 2147483647. Para usá-la no tabuleiro, pode-se fazer o seguinte:
+
    escrever "Divisor: "
 +
    ler divisor
  
<syntaxhighlight lang=c>
+
    se divisor = 0 entao
#include <stdlib.h>
+
        escrever "Nao pode dividir: divisor = 0 !!!"
 
+
    senao
int main() {
+
        resto <- dividendo % divisor
  int x, y;
+
        se resto = 0 entao
 
+
            quociente <- dividendo / divisor
  // gera dois números aleatórios entre 0 e 9, e guarda-os nas variáveis x e y
+
            escrever dividendo , " / " , divisor , " = " , quociente
  x = random() % 10;
+
        senao
  y = random() % 10;
+
            escrever "Nao pode fazer divisao inteira"
 
+
            escrever " (resto = " , resto , ")"
}
+
        fimse
 +
    fimse
 +
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
 +
*# <syntaxhighlight lang=text>
 +
inicio
 +
    inteiro termometro , barometro , tempo
  
A versão atual do jogo está assim:
+
    escrever "Qual a condição do termômetro: \n"
 +
    escrever "Digite 1 para baixando , 2 para estacionário e 3 para subindo. \n"
 +
    ler termometro
  
<syntaxhighlight lang=c>
+
    escrever "Informe a condição do barômetro: \n"
#include <stdio.h>
+
    escrever "Digite 1 para baixando , 2 para estacionário e 3 para subindo. \n"
#include <stdlib.h>
+
    ler barometro
  
#define MINAS 10
+
    tempo <- termometro*10 + barometro
#define LINHAS 10
 
#define COLUNAS 10
 
  
#define TEM_MINA 10
+
    escolhe tempo
 
+
        caso 11:
/*
+
            escrever "Chuvas abundantes e ventos de sul a sudoeste fortes"
*
+
        caso 12:
*/
+
            escrever "Chuva Provavel , ventos de sul a sudeste"
int main(int argc, char** argv) {
+
        caso 13:
    int tabuleiro[LINHAS][COLUNAS];
+
            escrever "Tempos Bons , ventos de sul a sudeste"
    int i, j;
+
        caso 21:
 
+
            escrever "Frente quente com chuva provavel"
    // Zerar todas as posições do tabuleiro !
+
        caso 22:
    i = 0;
+
            escrever "Tempo Incerto , ventos variaveis"
    while ( i < LINHAS) {
+
        caso 23:
         j = 0;
+
            escrever "Tempos Bons , ventos do leste frescos"
         while (j < COLUNAS) {
+
        caso 31:
             tabuleiro[i][j] = 0;
+
            escrever " Tempo instavel , aproximaçao de frente"
             j++;
+
         caso 32:
        }
+
            escrever "Tempo Mudando para bom , ventos de leste"
        i++;
+
         caso 33:
     }
+
             escrever "Tempos Bons , ventos quentes e secos"
 +
        defeito:
 +
             escrever "Utilize somente os algorismos de 1 a 3 para indicar as condiçoes do equipamentos"
 +
    fimescolhe
 +
fim
 +
</syntaxhighlight>
 +
*# <syntaxhighlight lang=text>
 +
inicio
 +
    // coeficientes do polinomio  [ax^2 + bx + c = 0 ]
 +
     real a , b , c
 
      
 
      
     // Colocar as minas aqui !!!
+
     escrever "Forneça os coeficientes da equação de 2o grau:\n"
 
+
     escrever "a="
     //Agora mostrar o tabuleiro que foi gerado
+
     ler a
 
+
     escrever "b="
     //i indica a linha, j a coluna
+
     ler b
     i = 0;
+
    escrever "c="
     while (i < LINHAS) {
+
    ler c
        // O while abaixo mostra todas as colunas da linha "i"
+
   
        j = 0;
+
    // equação do tipo [ bx + c = 0 ]
        while (j < COLUNAS) {
+
    se a = 0 entao
            if (tabuleiro[i][j] == TEM_MINA) {
+
        escrever " não é uma equação de 2o grau !!!"
                printf("* ");
+
    senao
            } else {
+
        // calcular o delta => interior da raiz
                if (tabuleiro[i][j] == 0) {
+
        real delta
                    printf(" ");
+
       
                } else {
+
        delta <- b ^ 2 - 4 * a * c
                    if ((tabuleiro[i][j] >= 1) && (tabuleiro[i][j] <= 8)) {
+
       
                        printf("%d ", tabuleiro[i][j]);
+
        // não existem raizes  reais de números negativos
                    }
+
         se delta < 0 entao
                }
+
            escrever " não tem raizes reais"
            }
+
         senao
            j++;
+
            // -----------  raiz dupla ----------------
         }
+
            se delta = 0 entao
 
+
                real x1
        printf("\n");
+
                x1 <- -b / 2 * a
         i++;
+
                escrever "\nraiz dupla : " , x1
    }
+
            senao
 
+
                // - ---------- duas raizes ---------------
    return (EXIT_SUCCESS);
+
                real x1 , x2
}
+
                x1 <- ( -b + raiz ( delta ) ) / 2 * a
</syntaxhighlight>
+
                x2 <- ( -b - raiz ( delta ) ) / 2 * a
 
+
                escrever "\nraiz x1 : " , x1
=== Meta desta semana ===
+
                escrever "\nraiz x2 : " , x2
 
+
            fimse//raiz dupla
Nesta semana o seu programa deve ser capaz de:
+
        fimse// delta >0
# Representar o tabuleiro com uma matriz de inteiros bidimensional.
+
    fimse// a <> 0
# Mostrar o tabuleiro na tela, indicando o que existe em cada casa. O tabuleiro deve ser apresentado  ''enfeitado'', o que significa que deve mostrar uma grade para separar as casas e a identificação de linhas e colunas. Linhas  devem ser identificadas numericamente, e colunas devem ser identificadas por letras (ex: primeira coluna=A, segunda coluna=B, ...).
+
fim
# Colocar minas aleatoriamente no tabuleiro.
 
 
 
O seu programa cumprindo as metas acima '''deve ser apresentado ao professor na próxima aula (16/11), já sendo parte da avaliação desta unidade'''.
 
 
 
== 16/11: As minas e o tabuleiro ==
 
 
 
Conteúdos abordados:
 
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c300.html declaração de variáveis]
 
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c940.html saída de dados na tela]
 
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c410.html estrutura de decisão: ''if'']
 
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c440.html estrutura de repetição: ''while'']
 
 
 
=== Dúvidas sobre random() ===
 
 
 
<syntaxhighlight lang=c>
 
#include <stdio.h>
 
#include <stdlib.h>
 
#include <sys/time.h>
 
 
 
int main() {
 
  int x,y,z;
 
  time_t t;
 
 
 
  // Lê o valor do relógio
 
  t = time(NULL);
 
 
 
  // Usa o valor do relógio como semente do gerador de números
 
  // pseudo-aleatórios.
 
  srandom(t);
 
 
 
  // Sorteia três números pseudo-aleatórios
 
  x = random() % 10;
 
  y = random() % 10;
 
  z = random() % 10;
 
 
 
  printf("x=%d, y=%d, z=%d\n", x, y, z);
 
}
 
 
</syntaxhighlight>
 
</syntaxhighlight>
=== Funções ===
+
*# <syntaxhighlight lang=text>
 
+
inicio
A função ''mostra_tabuleiro'' corresponde ao algoritmo para desenhar o tabuleiro na tela. O tabuleiro em si é representado pela variável ''tabuleiro'', que tem escopo global (visível em todas as funções do programa). Neste momento é bom ler um pouco mais sobre funções na linguagem C:
+
    inteiro num, bit
* [[SOP-funcoes|Texto introdutório sobre funções na linguagem C]]
+
    inteiro base
 +
   
 +
    escrever "Este algoritmo converte um número inteiro para sua representação binária.\n"
 +
    Escrever "O número deve estar entre 0 e 131071, e a representação binária\n"
 +
    escrever "terá 17 bits\n\n"
 +
    escrever "Digite o numero a ser convertido para binário: "
 +
    ler num
  
 
+
    base <- 65536
 
+
    enquanto base > 0 faz
=== Para fixar ===
+
        bit <- ( num / base ) % 2
 
+
        escrever bit, " "  
# Escreva um  programa para ler 10 números do teclado, e em seguida mostrar o maior e o menor número.
+
        base <- base / 2
# Reescreva o programa anterior, mas criando as funções "maior" e "menor", que retornam o maior e menor número de um vetor de tamanho arbitrário.
+
     fimenquanto
# Faça um  programa  que desenhe a seguinte figura na tela (use uma função para desenhar cada linha): <syntaxhighlight lang=text>
+
fim
     '
 
    *
 
  ***
 
  *****
 
*******
 
*********
 
*******
 
  *****
 
  ***
 
    *
 
 
</syntaxhighlight>
 
</syntaxhighlight>
# Até que ponto se poderiam usar funções para mostrar o tabuleiro ? Imagine que mostrar o tabuleiro fosse uma tarefa composta por 2 subtarefas:
+
*# <syntaxhighlight lang=text>
## ''Mostrar o estado de uma casa do tabuleiro''
+
inicio
## ''Mostrar o tabuleiro completo:'' mostrar todas as casas (usa subtarefa anterior).<br>Note que essas subtarefas correspondem à sequência do projeto até o momento. Um bom exercício seria modelar a tarefa de mostrar o tabuleiro usando uma função para cada subtarefa escrita acima.
+
    inteiro n , fat
 
+
     ler n
== 22/11: Contando minas vizinhas ==
+
     fat <- 1
 
+
     enquanto n > 1 faz
=== A contagem de minas ===
+
      fat <- fat * n
 
+
      n <- n - 1          
Para ajudar a visualizar o algoritmo de contagem de minas vizinhas, segue o fluxograma abaixo. As coordenadas ''(x,y)'' correspondem à casa cujas minas vizinhas se desejam contar. Veja sua semelhança com o [[SOP-2010-2-sobral#Zerando_o_tabuleiro|algoritmo para zerar o tabuleiro]].
+
     fimenquanto
 
 
[[imagem:Conta-minas.png|300px]]
 
 
 
A sugestão é por o algoritmo de contagem em uma [[SOP-funcoes|função]], e dentro do programa chamá-lo para cada casa do tabuleiro:
 
 
 
<syntaxhighlight lang=c>
 
#include <stdio.h>
 
#include <stdlib.h>
 
 
 
#define MINAS 10
 
#define LINHAS 10
 
#define COLUNAS 10
 
 
 
#define TEM_MINA 10
 
 
 
// O tabuleiro como variável global: necessário para poder ser usado e modificado por outras funções
 
int tabuleiro[LINHAS][COLUNAS];
 
 
 
 
 
// Função para contar as minas vizinhas da casa x, y
 
void conta(int x, int y) {
 
 
 
 
 
}
 
 
 
/*
 
*
 
*/
 
int main(int argc, char** argv) {
 
     int i, j;
 
 
 
     // Zerar todas as posições do tabuleiro !
 
     i = 0;
 
    while ( i < LINHAS) {
 
        j = 0;
 
        while (j < COLUNAS) {
 
            tabuleiro[i][j] = 0;
 
            j++;
 
        }
 
         i++;
 
     }
 
 
      
 
      
     // Colocar as minas aqui !!!
+
     escrever "Fatorial=" , fat
 
+
fim
    // contar as minas vizinhas de cada casa do tabuleiro
 
    i = 0;
 
    while ( i < LINHAS) {
 
        j = 0;
 
        while (j < COLUNAS) {
 
            // chama a função de contagem de minas, para contar as minas
 
            // vizinhas da casa com coordenadas i,j
 
            conta(i, j);
 
            j++;
 
        }
 
        i++;
 
    }
 
 
 
    //Agora mostrar o tabuleiro que foi gerado
 
 
</syntaxhighlight>
 
</syntaxhighlight>
 
+
*# <syntaxhighlight lang=text>
Obs: cuidado com o seguinte ao fazer o algoritmo de contagem de minas:
+
inicio
* Casas na borda do tabuleiro possuem menos casas vizinhas (casas fora do tabuleiro devem ser ignoradas).
+
    inteiro valor , menor , contador
* O algoritmo não pode ser aplicado em casas que contêm minas. Quer dizer, não faz sentido calcular as minas vizinhas de uma casa que tem uma mina.
+
    ler menor
 
+
    contador <- 9
Levando em conta as restrições acima, o algoritmo deve ficar parecido com o seguinte:
+
    enquanto contador > 0 faz
 
+
        ler valor
[[imagem:Conta-minas2.png|320px]]
+
        se valor < menor entao
 
+
            menor <- valor
== 23/11: Pensando no jogo completo !  ==
+
        fimse
 
+
        contador <- contador - 1
=== Topicos sobre linguagem C ===
+
    fimenquanto
 
+
    escrever "menor valor = ", menor
==== Estrutura de repetição ''for'' ====
+
fim
 
 
* Mais detalhes na [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c430.html apostila da UFMG]
 
 
 
A estrutura de repetição ''for'' costuma ser mais usada por programadores do que ''while''. Ao contrário de sua contraparte no Portugol (''para variavel de inicio ate fim ...''), a estrutura ''for'' possui grande flexibilidade para controle das repetições de um laço. Quer dizer, qualquer laço implementado com ''while'' pode ser também implementado com ''for''. O diferencial do ''for'' está na possibilidade de concentrar todas as instruções necessárias para controlar o laço.
 
 
 
A estrutura ''for'' pode ser declarada da seguinte forma:
 
 
 
<syntaxhighlight lang=c>
 
for (inicialização; condição; atualização) {
 
//comandos
 
}
 
 
</syntaxhighlight>
 
</syntaxhighlight>
 
+
*# <syntaxhighlight lang=text>
... sendo:
+
inicio
* '''inicialização:'''  instruções a serem executadas no início do laço (antes da primeira repetição)
+
    inteiro numero , n , resto <- 1
* '''condição:''' condição (expressão lógica) para a continuidade do laço. Deve ser verdadeira para que se execute mais uma repetição.
+
    escrever "Forneçaa um número: "
* '''atualização:''' instruções a serem executadas ao final de cada repetição
+
    ler numero
 
+
    n <- 2
Por exemplo, para mostrar os números de 1 a 10 na tela:
+
    enquanto n <= numero / 2 e resto =/= 0 faz
 
+
        resto <- numero % n
<syntaxhighlight lang=c>
+
        escrever "n=" , n , ": resto=" , resto , "\n"
  int x;
+
        n <- n + 1
 
+
    fimenquanto
  for (x=1; x < 11; x++) {
+
   
    printf("x=%d\n", x);
+
    se resto = 0 entao
  }
+
        escrever "nao primo: divisivel por " , n - 1
</syntaxhighlight>
+
    senao
 
+
        escrever "primo"
Veja no exemplo acima que tudo o que se precisa saber sobre o controle do laço está concentrado na declaração do ''for'':
+
    fimse
 
+
fim
<syntaxhighlight lang=c>
 
  for (x=1; x < 11; x++) {
 
 
</syntaxhighlight>
 
</syntaxhighlight>
 +
*# <syntaxhighlight lang=text>
 +
// Le 5 valores e identifica os dois maiores.
 +
inicio
 +
    inteiro valor , maior1 , maior2 , contador
 +
   
 +
    ler valor
 +
    maior1 <- valor
 +
   
 +
    ler valor
 +
    se valor > maior1 entao
 +
      maior2 <- maior1
 +
      maior1 <- valor
 +
    senao
 +
      maior2 <- valor
 +
    fimse
  
* ''inicialização (x=1):'' o laço inicia atribuindo o valor ''1'' à variável ''x''
+
    contador <- 3
* ''condição (x < 11):'' o laço continua enquanto o valor da variável ''x'' for menor que ''11''
+
    enquanto contador > 0 faz
* ''atualização (x++):'' ao final de cada repetição, o valor da variável ''x'' é incrementado
+
        ler valor
+
        se valor > maior1 entao
Muitas possibilidades existem para o uso de ''for''. Veja este outro exemplo:
+
            maior2 <- maior1
 +
            maior1 <- valor
 +
        senao
 +
            se valor > maior2 entao
 +
                maior2 <- valor
 +
            fimse
 +
        fimse
 +
        contador <- contador - 1
 +
    fimenquanto
  
<syntaxhighlight lang=c>
+
    escrever "maior valor = " , maior1
  char c;
+
     escrever "\nsegundo maior valor = " , maior2
 
+
fim
  for (c = 'A'; c < 'K'; c++) {
 
     printf("%c ", c);
 
  }
 
 
</syntaxhighlight>
 
</syntaxhighlight>
  
 
+
== 25/05: Avaliação ==
O programa do Campo Minado com o uso de ''for'' ao invés de ''while'' fica assim:
 
  
<syntaxhighlight lang=c>
+
No laboratório ...
#include <stdio.h>
 
#include <stdlib.h>
 
  
#define MINAS 10
+
* [http://tele.sj.ifsc.edu.br/~msobral/prog/prova.html Prova]
#define LINHAS 10
 
#define COLUNAS 10
 
  
/*
+
=== Prova resolvida ===
*
 
*/
 
int tabuleiro[LINHAS][COLUNAS];
 
  
void conta(int x, int y) {
+
1) Um programa em uma estação meteorológica converte os valores lidos de um higrômetro para um indicativo de umidade do ar. A tabela de conversão segue abaixo:
  
}
+
{| border="1" cellpadding="2"
 +
!Valor do higrômetro
 +
!Indicativo de umidade
 +
|-
 +
|0 a 0.3 || muito baixa
 +
|-
 +
|0.3 a 0.5 || baixa
 +
|-
 +
|0.5 a 0.8 || normal
 +
|-
 +
|0.8 a 1 || alta
 +
|-
 +
|1 || precipitação
 +
|}
  
int main(int argc, char** argv) {
+
Escreva esse programa, que deve simular a leitura do higrômetro pelo teclado e mostrar o indicativo de umidade na tela.
    int i, j;
 
  
     // zerar todas as posições do tabuleiro !
+
<syntaxhighlight lang=text>
     for (i=0; i < LINHAS; i++) {
+
inicio
         for (j=0; j < COLUNAS; j++) {
+
    real h
             tabuleiro[i][j] = 0;
+
   
         }
+
    escrever " digite um valor de 0 a 1:  " ,
     }
+
    ler h
 +
   
 +
     se h = 1 entao
 +
        escrever "chuva" ,
 +
     senao
 +
        se h <= 0.3 entao
 +
            escrever "umidade muito baixa" ,
 +
         senao
 +
            se h <= 0.5 entao
 +
                escrever "umidade baixa" ,
 +
             senao
 +
                se h <= 0.8 entao
 +
                    escrever "umidade normal"
 +
                senao
 +
                    se h < 1 entao
 +
                        escrever "umidade alta"
 +
                       
 +
                    fimse
 +
                fimse
 +
            fimse
 +
         fimse
 +
     fimse
 +
fim
 +
</syntaxhighlight>
  
    // Colocar as minas aqui !!!
+
2) Um programa possui o seguinte vetor de inteiros guardado em memória:
  
    // Contar as minas vizinhas
+
{10,12,7,4,5,9,2,3,1,3,4,2,2,9}
    for (i=0; i < LINHAS; i++) {
 
        for (j=0; j < COLUNAS; j++) {
 
            conta(i,j);
 
        }
 
    }
 
  
    //Agora mostrar o tabuleiro que foi gerado
+
Esse programa deve ler uma sequência de 4 números pelo teclado, e procurá-la dentro do vetor que está em memória. Se a sequência for encontrada, a posição em que ela inicia dentro do vetor deve ser mostrada.
  
    //i indica a linha, j a coluna
+
<syntaxhighlight lang=text>
    for (i=0; i < LINHAS; i++) {
+
inicio
        // O while abaixo mostra todas as colunas da linha "i"
+
  inteiro numeros[14] <- {10,12,7,4,5,9,2,3,1,3,4,2,2,9}
      for (j=0; i < COLUNAS; j++) {
+
  inteiro v[4]
            if (tabuleiro[i][j] == 10) {
+
  inteiro i, j
                printf("* ");
+
 
            } else {
+
  Escrever "Digite 4 numeros inteiros:"
                if (tabuleiro[i][j] == 0) {
+
  para i de 0 ate 3 passo 1
                    printf("  ");
+
    ler v[i]
                } else {
+
  proximo
                    if ((tabuleiro[i][j] >= 1) && (tabuleiro[i][j] <= 8)) {
+
 
                        printf("%d ", tabuleiro[i][j]);
+
  para j de 0 ate 10 passo 1
                    }
+
    i <- 0
                }
+
    enquanto i < 4 E v[i] = numeros[j+i] faz
            }
+
      i <- i + 1
        }
+
    fimenquanto
        printf("\n");
+
    se i = 4 entao
    }
+
      escrever "Encontrou na posicao ", j
 
+
      fim
    return (EXIT_SUCCESS);
+
    fimse
}
+
  proximo
 +
  escrever "Nao encontrou em nenhuma posicao"
 +
fim
 
</syntaxhighlight>
 
</syntaxhighlight>
  
==== Condições e operadores lógicos ====
+
3) Um número primo é um número divisível somente por 1 ou por si mesmo. Quer dizer, se tentar dividi-lo por qualquer valor maior que 1 e menor que esse número, o resto será diferente de zero. Exemplos de números primos são 2, 3, 5, 7 e 11. Escreva um programa que leia um número pelo teclado e informe se ele é primo.
  
* Maiores detalhes na [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c360.html apostila da UFMG]
+
<syntaxhighlight lang=text>
 +
inicio
 +
    inteiro numero , n
  
Obs: cada condição em linguagem C deve ser envolvida por parênteses.
+
    escrever "Forneça um número: "
 +
    ler numero
  
Necessários para expressar condições a serem usadas principalmente com ''if'' e ''while''.
+
    n <- 2 
 
+
    enquanto n <= numero / 2 E resto =/= 0 faz     
{| border="1" cellpadding="2"
+
        resto <- numero % n
!Portugol
+
        n <- n + 1
!C
+
    fimenquanto
!Exemplo
+
   
|-
+
    se resto = 0 entao
|E||&&|| <syntaxhighlight lang=c>
+
        escrever "nao primo: divisivel por " , n - 1
if ((x >= 0) && (x <= 9)) {
+
    senao
  printf("coordenada x é válida\n");
+
        escrever "primo"
}</syntaxhighlight>
+
    fimse
|-
+
fim
|OU||<nowiki>||</nowiki>||<syntaxhighlight lang=c>if ((x < 0) || (x > 9)) {
+
</syntaxhighlight>
  printf("coordenada x é inválida\n");
 
}</syntaxhighlight>
 
|-
 
|NAO||!||<syntaxhighlight lang=c>if (!((x < 0) || (x > 9))) {
 
  printf("coordenada x é válida\n");
 
}</syntaxhighlight>  
 
|-
 
|}
 
  
=== Uma versão alternativa para a contagem de minas ===
+
... uma versão com uma pequena melhoria:
  
A versão abaixo foi criada pela Marine e Nathany. Apesar de parecida com o [[SOP-2010-2-sobral#A_contagem_de_minas|algoritmo proposto pelo professor]], possui uma diferença importante que a torna mais eficiente.
+
<syntaxhighlight lang=text>
 +
inicio
 +
    inteiro numero, n, resto
  
[[imagem:Conta-minas-nathany-marine.png|320px]]
+
    escrever "Forneça um número: "
 +
    ler numero
  
== 29/11: Pensando no jogo completo ... ==
+
   
 +
    resto <- numero % 2
 +
    se resto =/= 0 entao
 +
      n <- 1
 +
      enquanto n <= numero / 2 E resto =/= 0 faz     
 +
          n <- n + 2
 +
          resto <- numero % n
 +
      fimenquanto
 +
     
 +
      se resto = 0 entao
 +
          escrever "nao primo: divisivel por " , n
 +
      senao
 +
          escrever "primo"
 +
      fimse
 +
    senao
 +
      escrever "nao primo: divisivel por 2"
 +
    fimse
 +
fim
 +
</syntaxhighlight>
  
* Continuando [[SOP-funcoes|funções]]: variáveis locais e globais, escopo de variáveis.
+
4) Jogo de Pedra, papel e tesoura: nesse jogo cada jogador faz sua escolha, e vence aquele que escolher um objeto que seja capaz de vencer o outro:
  
=== Escondendo as casas não pisadas ===
+
<syntaxhighlight lang=text>
 +
* Tesoura corta papel
 +
* Pedra quebra tesoura
 +
* Papel embrulha a pedra
 +
</syntaxhighlight>
  
No momento você deve já conseguir mostrar todo o tabuleiro, porém no jogo apenas as casas já pisadas devem ser reveladas. Pense em como modelar o seu tabuleiro de forma a esconder as casas ainda não pisadas.
+
Faça um algoritmo que pergunte ao usuário o objeto escolhido, e em seguida faça o computador escolher o seu próprio objeto (dica: use o gerador de números aleatórios visto no jogo do par ou ímpar). Ao final o algoritmo deve informar o vencedor.  
  
Opções:
+
<syntaxhighlight lang=text>
# '''''Criar uma matriz de controle:''''' cada casa dessa nova matriz informa se a casa correspondente do tabuleiro está revelada. Por exemplo, se a casa (1,2) na matriz de controle tiver o valor 0 (zero), então a casa (1,2) do tabuleiro está escondida, e se tiver o valor 1, a casa (1,2) do tabuleiro está revelada.
+
inicio
# '''''Explorar os códigos numéricos das casas:''''' os códigos numéricos das casas do tabuleiro poderiam ser estendidos para informar se uma casa está escondida ou revelada. Por exemplo, se o código de uma casa for menor do que 100, ela está escondida, caso contrário está revelada. Assim, se casa (1,2) tiver o valor 3, significa que possui 3 minas vizinhas porém ainda está escondida, e se tiver o valor 103 significa que possui 3 minas vizinhas e já está revelada.
+
    inteiro lancecomputador , lancejogador
 +
    logico jogadorvenceu
 +
   
 +
    escrever "Escolha papel (1) , pedra (2) ou tesoura (3): "
 +
    ler lancejogador
 +
    se lancejogador > 3 ou lancejogador < 1 entao
 +
        escrever "Lance inválido !!! (deve digitar um número entre 1 e 3)\n\n"
 +
    senao
 +
        lancecomputador <- 1 + 2 * aleatorio ( )
 +
        escrever "Computador escolheu: " , lancecomputador , "\n"
 +
        se lancejogador = lancecomputador entao
 +
            escrever "Empate !\n\n"
 +
        senao
 +
          jogadorvenceu <- falso
 +
          escolhe lancejogador
 +
              caso 1:
 +
                  se lancecomputador = 2 entao
 +
                      jogadorvenceu <- verdadeiro
 +
                  fimse
 +
              caso 2:
 +
                  se lancecomputador = 3 entao
 +
                      jogadorvenceu <- verdadeiro
 +
                  fimse
 +
              caso 3:
 +
                  se lancecomputador = 1 entao
 +
                      jogadorvenceu <- verdadeiro
 +
                  fimse
 +
          fimescolhe
 +
          escrever "Vencedor: "
 +
          se jogadorvenceu entao
 +
              escrever "jogador\n\n"
 +
          senao
 +
              escrever "computador\n\n"
 +
          fimse
 +
      fimse
 +
    fimse
 +
fim
 +
</syntaxhighlight>
  
== 30/11: Pensando no jogo completo ... ==
+
... uma outra solução:
  
* Continuando [[SOP-funcoes|funções]]: variáveis locais e globais, escopo de variáveis.
+
<code>
* [[SOP-stdio|Entrada de dados pelo teclado]]
+
inicio
 +
    inteiro lancecomputador , lancejogador
 +
    logico jogadorvenceu
 +
    texto vencedor , opcao
 +
   
 +
    escrever "Jogo de Papel , Pedra e Tesoura\n\n"
 +
    escrever "Escolha papel (1) , pedra (2) ou tesoura (3): "
 +
    ler lancejogador
 +
    se lancejogador > 3 ou lancejogador < 1 entao
 +
        escrever "Lance inválido !!! (deve digitar um número entre 1 e 3)\n\n"
 +
    senao
 +
        lancecomputador <- 1 + 2 * aleatorio ( )
 +
        escrever "Computador escolheu: " , lancecomputador , "\n"
 +
        se lancejogador = lancecomputador entao
 +
            escrever "Empate !\n\n"
 +
        senao
 +
            escrever "Vencedor: "
 +
            // repare em como se determina o vencedor nesta versao do jogo: a condicao abaixo
 +
            // é verdadeira sempre que o lance do jogador estiver uma unidade atrás do computador:
 +
            //
 +
            // Jogador    Computador
 +
            //    1            2
 +
            //    2            3
 +
            //    3            1 (nesta última preciso considerar que a contagem é circular)
 +
               
 +
            se (lanceJogador%3 + 1) = lanceComputador entao
 +
                escrever "jogador\n\n"
 +
            senao
 +
                escrever "computador\n\n"
 +
            fimse
 +
        fimse
 +
    fimse
 +
fim
 +
</syntaxhighlight>
  
=== Organizando o programa ===
+
5) Um programa somente pode ser usado por usuários autorizados. Os usuários e seuas senhas estão armazenados em uma tabela dentro do próprio programa. Escreva o algoritmo desse programa que pede o usuário e senha pelo teclado, consulta a tabela de usuários e depois informa se o acesso foi concedido ou negado. Os usuários e respectivas senhas estão mostrados abaixo:
  
Nesse momento seu programa deve estar ficando comprido, e já começando a se mostrar difícil de ler. Para torná-lo organizado e compreensível, deve ser reorganizado usando [[SOP-funcoes|funções]]:
+
{| border="1" cellpadding="2"
 +
!Usuário
 +
!Senha
 +
|-
 +
|joao || tainha
 +
|-
 +
|maria || pirao
 +
|-
 +
|maneca || onibus
 +
|-
 +
|bilica || bilro
 +
|-
 +
|}
  
<syntaxhighlight lang=c>
+
Obs: essa tabela pode ser modificada futuramente, então o algoritmo deve conseguir trabalhar com quaisquer usuários e senhas que ali sejam armazenados. Isso é, mesmo que essa tabela tenha seu conteúdo alterado, o algoritmo não pode ser modificado.
void inicia_tabuleiro() {
 
}
 
  
void mostra_tabuleiro(int tudo) {
+
<syntaxhighlight lang=text>
}
+
inicio
 +
  texto usuarios <- {"joao", "maria", "maneca", "bilica"}
 +
  texto senhas <- {"tainha", "pirao", "onibus", "bilro"}
 +
  texto login, umaSenha
 +
  inteiro i
 +
  logico OK <- falso
 +
 
 +
  escrever "Usuario:"
 +
  ler login
 +
 
 +
  escrever "Senha:"
 +
  ler umaSenha
 +
 
 +
  enquanto i < 4 E nao OK faz
 +
    ok <- usuarios[i] = login
 +
    i <- i + 1
 +
  fimenquanto
  
int main() {
+
  se ok entao
   // cria o tabuleiro, pondo as minas e contando as minas vizinhas de
+
    ok <- senhas[i] = umaSenha
   // cada casa
+
  fimse
   inicia_tabuleiro();
+
 
 +
   se ok entao
 +
    escrever "acesso concedido"
 +
   senao
 +
    escrever "acesso negado"
 +
   fimse
 
    
 
    
  // Mostra o tabuleiro que foi criado
+
fim
  // O argumento da função serve para forçar a mostrar todas as casas
 
  // (mesmo as escondidas), ou mostrar somente as reveladas.
 
  // Se for 1, mostra todas as casas.
 
  // Se for 0, mostra somente as reveladas.
 
  mostra_tabuleiro(1);
 
}
 
 
</syntaxhighlight>
 
</syntaxhighlight>
  
=== Retomando o laço principal do jogo ... ===
+
=== Conceitos ===
  
Como apresentado na [[SOP-2010-2-sobral#O_la.C3.A7o_principal_do_jogo_...|aula de 08/11]], o jogo funciona com um laço principal, que lê as coordenadas da casa a ser pisada ou marcada e atualiza o tabuleiro apropriadamente:
+
''Legenda:''
 +
* '''T:''' questão correta
 +
* '''P:''' questão parcialmente correta
 +
* '''N:''' questão incorreta ou em branco
  
Note que nesse laço devem-se contabilizar quantas minas foram realmente descobertas - o que não corresponde necessariamente a quantas minas foram  marcadas ... A quantidade de minas descobertas é necessária para decidir se o jogo já acabou.
+
{| border="1" cellpadding="2"
 
+
!Aluno
[[imagem:Fluxo-Campo-Minado.png|400px]]
+
!Conceito
 
+
!Questão 1
A leitura das coordenadas deve ser feita usando a função [[SOP-stdio#Explorando_scanf_para_ler_dados_do_teclado|scanf]].
+
!Questão 2
 
+
!Questão 3
=== Pisando e marcando casas ===
+
!Questão 4
 
+
!Questão 5
O jogador pode pisar em uma casa. Ao pisar em uma casa com mina, o jogador perde e o jogo acaba. Se pisar em uma casa com minas vizinhas, o jogo revela a contagem de minas vizinhas daquela casa. Mas se a casa pisada não tiver minas vizinhas, o jogo deve revelar todas as casas vizinhas na mesma condição, até o limite de casas que possuem minas vizinhas. Na figura abaixo, pisou-se na casa que está sob o ponteiro do ''mouse''. Note que todas as casas ao redor também foram reveladas, até alcançarem-se casas que têm minas vizinhas.
+
|-
 
+
|Alfredo || D || T (mas não da forma mais eficiente) || N || N || N || N
[[imagem:Minas-pisadas.png]]
+
|-
 
+
|Ângelo || D || T (mas não da forma mais eficiente) || N || P || N || N
Pense em como ''abrir'' as casas vazias em torno da casa pisada ...
+
  |-
 
+
  |Beatriz || D || N || N || P (primos somente menores que 12)|| N ||N
O jogador pode também marcar uma casa, indicando que acredita ter ali uma mina. Essa casa continua escondida, porém deve ser mostrado que possui uma bandeira, como mostrado na figura abaixo. Se o jogador descobrir todas as minas, o jogo termina com sua vitória. Como se podem representar essas bandeiras no tabuleiro ?
 
 
 
[[imagem:Casas-marcadas.png]]
 
 
 
== 06/12: Pensando no jogo completo ... ==
 
 
 
Uma vez criado o [[SOP-2010-2-sobral#Retomando_o_la.C3.A7o_principal_do_jogo_...|laço principal do jogo]], em que se lêem coordenadas de casas a serem pisadas até que o jogo termine, faltam alguns refinamentos. São eles:
 
# Ao pisar numa casa que não possui minas vizinhas, devem-se abrir todas as casas adjacentes até encontrar casa que possuam minas vizinhas.
 
# Devem-se contabilizar as minas descobertas (casas marcadas), pois se todas as minas tiverem sido marcadas o jogo termina com vitória do jogador.
 
 
 
=== Abrindo casas que não possuem minas vizinhas ===
 
 
 
Ao se pisar em uma casa que não possui minas vizinhas, devem-se abrir recursivamente as casas adjacentes até encontrar casa com minas vizinhas. As figuras a seguir mostram como seria a abertura das casas (em vermelho a casa a ser aberta, e em hachurado as casas adjacentes):
 
 
 
[[imagem:Abre-1.png]]<br><br>
 
''Início: abrindo a casa pisada e testando as casas adjacentes''
 
 
 
 
 
 
 
[[imagem:Abre-2.png|300px]]<br>
 
''Aplicando a abertura de casa à cada casa adjacente''
 
 
 
 
 
 
 
[[imagem:Abre-3.png|300px]]<br>
 
''Novamente aplicando a abertura de casa às casas adjacentes ...''
 
 
 
 
 
O algoritmo que faz essa abertura de casas pode ser expresso da seguinte forma (note a recorrência, quando o algoritmo chama si próprio):
 
 
 
 
 
[[imagem:Abre-casas.png|275px]]
 
 
 
=== Mostrando o tempo decorrido ===
 
 
 
Para mostrar o tempo de jogo decorrido, devem-se contabilizar quantos segundos passaram desde que o jogo começou. Assim, deve-se ler o relógio do computador no início do jogo, e a cada vez que se precisar mostrar o tempo de jogo. Para ler o relógio pode-se usar a função [http://manpages.ubuntu.com/manpages/lucid/en/man2/time.2.html time] (já usada no [[SOP-2010-2-sobral#D.C3.BAvidas_sobre_random.28.29|algoritmo para colocar minas aleatoriamente]]). A contagem de quantos segundos se passaram se resume portanto a ler o relógio e subtrair o valor do relógio lido no início do programa, como no exemplo abaixo:
 
 
 
<syntaxhighlight lang=c>
 
#include <time.h>
 
#include <stdio.h>
 
 
 
int main() {
 
  time_t inicio;
 
  time_t agora;
 
 
 
  inicio = time(NULL);
 
 
 
  // faz alguma coisa
 
 
 
  agora = time(NULL);
 
 
 
  printf("Já passaram %d segundos desde o inicio deste programa ...\n", agora - inicio); 
 
}
 
</syntaxhighlight>
 
 
 
Além de contar o tempo de jogo decorrido, é necessário mostrá-lo em um formato claro para o jogador. Isso quer dizer, mostrar o tempo na forma ''"horas:minutos:segundos"'' ao invés de simplesmente a contagem de segundos. Por exemplo, se já transcorreram 143 segundos, deve-se mostrar ''"00:02:23"''. Para converter a contagem de segundos para esse formato você pode aproveitar o algoritmo de conversão de tempo proposto em um [[SOP-2010-2-sobral#Atividade_5|exercício de Lógica de Programação]]. Para formatar o horário como indicado, você pode conferir a [[SOP-stdio|explicação sobre printf]].
 
 
 
=== Tópico sobre linguagem C: caracteres e strings ===
 
 
 
Caracteres (tipo de dados '''''char''''') seguem a codificação [http://pt.wikipedia.org/wiki/ASCII ASCII].
 
 
 
''Strings'' são o equivalente ao tipo ''Texto'' do Portugol.
 
 
 
* [[SOP-strings|Strings]]: um texto introdutório
 
* Ver também:  [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/c500.html capítulo sobre ''strings'' no curso da UFMG].
 
 
 
==== Para fixar ====
 
 
 
# Faça um  programa que mostre a tabela ASCII: cada caractere com seu correspondente código numérico.
 
# Escreva um programa que leia separadamente o nome e o sobrenome de uma pessoa, e em seguida mostre-os da seguinte forma na tela: ''sobrenome, nome''.
 
# Escreva um programa para resolver a questão 2 da [[SOP-2010-1-sobral#12.2F05:_2a_avalia.C3.A7.C3.A3o|2a avaliação]].
 
# Escreva um programa que leia uma palavra do teclado, e em seguida mostre-a em ordem invertida.
 
# Faça um programa que leia uma palavra do teclado, e em seguida converta-a para maiúsculas.
 
# Faça um programa para ler uma frase do teclado, e contar quantas palavras nela existem.
 
 
 
== 07/12: Pensando no jogo completo ==
 
 
 
'''ATENÇÃO: preparar para apresentar o projeto na próxima 2a feira (13/12)'''
 
 
 
 
 
=== Tópicos em linguagem C: estruturas de dados (criação de novos tpos de dados) ===
 
 
 
* [[SOP-struct|Introdução a estruturas de dados em C]]
 
* [http://www.ead.cpdee.ufmg.br/cursos/C/aulas/cb00.html Capítulo sobre estruturas de dados no curso da UFMG]
 
 
 
== 13/12: Últimos ajustes ... ==
 
 
 
== 14/12: Apresentação ==
 
 
 
 
 
Na próxima semana, na 3a feira (14/12), vocês deverão apresentar os projetos sobre o campo minado. A apresentação será individual, em que entrevistarei cada aluno sobre sua participação no trabalho. Assim, se na entrevista for demonstrado que o aluno teve participação ativa no desenvolvimento do programa e domina o entendimento de como ele funciona, então receberá o conceito dado ao trabalho. Se não mostrar que entende como ele funciona, então ficará com conceito D e terá que fazer a prova de recuperação.
 
 
 
Para avaliar o trabalho, irei conferir se:
 
 
 
# O jogo funciona como especificado (ver [[SOP-2010-2-sobral#Retomando_o_la.C3.A7o_principal_do_jogo_...|laço principal do jogo na Wiki]]):
 
## O tabuleiro é criado e inicializado corretamente
 
## O tabuleiro é apresentado na tela conforme especificado na wiki (linhas como números e colunas como letras, grade, casas escondidas, reveladas ou marcadas com bandeiras)
 
## O programa lê as coordenadas de casas fornecidas pelo jogador, e executa corretamente a ação solicitada (pisar ou marcar), além de conferir se as coordenadas são válidas
 
## O jogo termina se uma mina  for pisada, e nesse caso revelando todas as casas do tabuleiro
 
## O jogo termina se o jogador descobrir todas as minas: se as únicas casas não reveladas forem exatamente as casas com minas que podem estar marcadas ou não com bandeiras)
 
## Se ao pisar numa casa sem minas vizinhas, as casas adjacentes são reveladas recursivamente até encontrar casas que tenham minas vizinhas.
 
# O programa está organizado e estruturado com funções
 
 
 
 
 
Ítens extras, que são opcionais e aumentarão o conceito final da disciplina se forem feitos, são:
 
 
 
* Mostrar o tempo de jogo decorrido sempre que for ler novas coordenadas do jogador ([[SOP-2010-2-sobral#Mostrando_o_tempo_decorrido|ver na wiki dicas de como fazer]])
 
* Ter níveis de dificuldade do jogo:
 
** ''Fácil:'' tabuleiro 10 x 10 com 10 minas
 
** ''Médio:'' tabuleiro 15 x 15 com 15 minas
 
** ''Difícil:'' tabuleiro 20 x 20 com 30 minas
 
 
 
A prova de recuperação será dia 20/12 (2a feira), e terá ao menos quatro questões sobre programação em linguagem C a serem resolvidas em laboratório. Essa prova terá que ser resolvida iniciando às 7:30 e terminando no máximo às 10:30 h.
 
 
 
== Conceitos do projeto ==
 
 
 
{| border="1" cellpadding="2"
 
!Aluno
 
!Conceito
 
 
  |-
 
  |-
  |Fernando || C
+
  |Bruno da Silva || D|| N (erros de sintaxe) || N || T || N (copiado de um exemplo do professor) || N
 
  |-
 
  |-
  |Gabriel || D*
+
  |Bruno || D || N || N || N || N || N
 
  |-
 
  |-
  |Levi || D*
+
  |Caroline || D || T || N || N || N || N
 
  |-
 
  |-
  |Lindalvo || C
+
  |Danilo || B ||T (mas não da forma mais eficiente) || T (mas não da forma mais eficiente)|| N (idêntico ao do Gabriel)|| T || T (mas não da forma mais eficiente)
 
  |-
 
  |-
  |Marcos || A
+
  |Dayze || D || N || N || N || N || N
 
  |-
 
  |-
  |Marine || D
+
  |Fabiana || C || T (mas não da forma mais eficiente)|| P || N || T ||N
 
  |-
 
  |-
  |Mario Allan || A
+
  |Felipe || C || T || N || N || P (computador deveria jogar) || P (funciona só pra 4 contas)
 
  |-
 
  |-
  |Mário André || A
+
  |Gabriel || D || T (mas não da forma mais eficiente) || N || N (idêntico ao do Danilo)|| N|| P (funciona só pra 4 contas)
 
  |-
 
  |-
  |Mário Sérgio || D
+
  |Grazielle || D || N || N || N || N || N
 
  |-
 
  |-
  |Maykon || B
+
  |Jayson || D || N || N || N || N || P (funciona só pra 4 contas)
 
  |-
 
  |-
  |Nathany || D
+
  |Juliano || C|| T (mas não da forma mais eficiente)||N||N ||T|| P (funciona só pra 4 contas)
 
  |-
 
  |-
  |Paulo Igor || D*
+
  |Leandro || D|| T (mas não da forma mais eficiente)|| N|| N|| N||N
 
  |-
 
  |-
  |Ricardo || D
+
  |Leonardo || D||P (condições trocadas) || N|| N|| P (não indica o vencedor)||N
 
  |-
 
  |-
|Roberto || D*
+
|}
|-
 
|Thiago Martins || D*
 
|-
 
|Thiago Ramos || D*
 
|-
 
|Vinicius Kachniacz || D*
 
|-
 
|Vinicius Rodrigues || D
 
|-
 
|}
 
  
''Obs: D* = não apresentou o projeto (desistente)''
+
== 26/05: Começo do projeto ==
  
== 20/12: Recuperação ==
+
Para referência: [http://www.ead.cpdee.ufmg.br/cursos/C/c.html apostila online sobre linguagem C].
 
 
A prova de recuperação terá ao menos quatro questões sobre programação em linguagem C a serem resolvidas em laboratório. Essa prova terá que ser resolvida iniciando às 7:30 e terminando no máximo às 10:30 h. Essa prova será a mesma para quem precisar recuperar Lógica de Programação.
 
 
 
*[http://www.sj.ifsc.edu.br/~msobral/SOP/avaliacoes/rec-2010-2.pdf Prova de recuperação]
 

Edição atual tal como às 20h45min de 6 de julho de 2011

Introdução à Programação - 2011-1

Informações gerais

Professor: Marcelo Maia Sobral
Email: msobral@gmail.com
Skype: mm-sobral
Lista de email (forum): prg-ifsc@googlegroups.com
Atendimento paralelo: 4a feira 10:00 - 11:30 h, 5a feira 8:00 - 9:30 h e 13:30 - 15:30 h (no Laboratório de Desenvolvimento de Tele)
Reavaliação (recuperação): no final do semestre
IMPORTANTE: o direito de recuperar uma avaliação em que se faltou somente existe mediante justificativa reconhecida pela coordenação. Assim, deve-se protocolar a justificativa no prazo de 48 horas, contando da data e horário da avaliação, e aguardar o parecer da coordenação. O não cumprimento desse procedimento implica a impossibilidade de fazer a recuperação, e assim a reprovação na disciplina.

Softwares

Será usado como plataforma de estudo o sistema operacional Ubuntu Linux 10.04 LTS ou posterior. Para obtê-lo há essas opções:

  1. Trazer um CD-R virgem para que eu faça a cópia aqui no IFSC
  2. Fazer o download por conta própria (aprox. 700 MB)
  3. Usar uma máquina virtual do VirtualBox já preparada por mim (menos recomendado, pois o Linux roda mais lento)
    • Trazer um DVD-R ou pendrive com ao menos 4 GB livres.
    • Instalar o VirtualBox em seu computador para executar a máquina virtual

ATENÇÃO: é muito importante que se providencie o quanto antes a instalação do Ubuntu em seu computador. Sem ele você não poderá fazer os exercícios sugeridos, o que atrapalhará seu aproveitamento na disciplina ! O bom andamento do estudo depende muito de não deixar acumular o conteúdo e os exercícios. Acostume a criar uma rotina de estudo, procurando resolver os problemas apresentados e procurando o professor (ou contatando-o por email) para tirar dúvidas.

Listas de exercícios

Referências adicionais

Aulas

16/03: Introdução

Apresentação da disciplina: plano de ensino, avaliação, abordagem pedagógica.

Assunto: Lógica de programação

Referências auxiliares:


Um primeiro algoritmo


Videos sobre algoritmos:

Problemas exemplo

Problema dos três recipientes

Há três recipientes com tamanhos distintos: um com 8 litros, outro com 5 litros e o terceiro com 3 litros. O recipiente com 8 litros está completamente cheio. Deseja-se colocar 4 litros em dois recipientes. Considere que os recipientes não são graduados.

Problema da travessia

Um barqueiro precisa levar um saco de milho, uma galinha e uma raposa para o outro lado do rio. Porém o barco somente é capaz de levar uma coisa de cada vez (além do barqueiro). Qual a sequência de travessias necessário para atravessar o milho, a galinha e a raposa ?

Torres de Hanoi

Há três hastes. Uma das hastes serve de suporte para três discos de tamanhos diferentes. Um disco menor sempre é colocado sobre um disco maior. A figura abaixo ilustra as hastes e os discos:

Hanoi.png

Desejam-se mover os três discos para a haste da direita. Porém só pode se mover um disco por vez, e um disco maior nunca pode ficar sobre um disco menor.

Operação possível: Move disco para haste

Qual a sequência de operações para mover os discos de uma haste para outra ?

Leitura adicional

17/03: Algoritmos

Para criar algoritmos, deve-se primeiro entender o que são instruções e sequências lógicas;

O jogo LightBot mostra de uma forma divertida como criar pequenos algoritmos. Nesse jogo o robô deve se movimentar de acordo com uma sequência de instruções elementares definidas pelo jogador. Apesar de sua simplicidade, ele pode se tornar bastante desafiador ! Até que fase desse jogo você consegue chegar ?

Lightbot.png

Desenhando figuras geométricas

  1. Scratch é um software educacional para ajudar no ensino de matemática, geometria e introdução à programação. Com ele pequenos programas podem ser escritos de foram visual, com instruções representadas por blocos que se encaixam como Lego. Ele possibilita fazer desenhos facilmente, seguindo um programa com instruções de desenho. Use-o para desenhar estas figuras:
    • triângulo equilátero
    • triângulo isósceles
    • quadrado
    • hexágono
    • quadrado com vértices interligados
    • Um círculo

Scratch.png


  • Agora tente algo mais avançado:
    • Desenhe um triângulo equilátero, porém perguntando na tela qual o tamanho do lado.
    • repita o desenho do triângulo, porém fazendo-o lentamente: espere 1 segundo após desenhar cada lado do triângulo.
    • Faça com que um pequeno traço se movimente de um lado a outro do palco.
    • Faça com que um pequeno traço se movimente em círculo indefinidamente.
    • Faça com que uma bola role pela horizontal. Insira quatro raios na bola para ajudar no efeito visual de movimento.

Atividade para casa

Faça as figuras geométricas indicadas na aula !

23/03: Começando os primeiros algoritmos ...

Algoritmo é uma sequência lógica de instruções, a qual possui um início e um fim.

Sequência lógica é uma sequência correta de instruções capaz de gerar o resultado esperado.


A escrita ou projeto de algoritmos se faz com:

  • Estruturas de controle: comandos que modificam uma sequência de instruções
  • Estruturas de dados: dados (valores) usados e modificados durante a execução do algoritmo.


Para introduzir esses conceitos, nada melhor que um pequeno projeto ...


Projeto: um jogo muito simples

Você conhece o jogo clássico Space Invaders ?

Spaceinvaders.jpg


Pros padrões atuais esse é um jogo muito simples. Você conseguiria reproduzi-lo, mesmo que simplificado, no Scratch ? Ele poderia começar assim:

Jogo1-scratch.gif


  1. O robô se movimenta na horizontal, comandado pelas teclas seta pra direita e seta pra esquerda.
  2. O helicóptero se movimenta de um lado a outro constantemente, refletindo nas bordas.
  3. Ao teclar espaço, um tiro sai do robô em direção ao topo do palco
  4. Se o tiro acertar o helicóptero, o jogo termina.


O que você precisa para fazer esse jogo ?

  1. Movimento do helicóptero.
  2. Movimento do robô comandado pelo teclado.
  3. Acionamento do tiro.
  4. Detecção se o tirou acertou o helicóptero.

Mãos à obra !

24/03: Introduzindo algoritmos: variáveis e expressões

Variáveis são usadas em algoritmos para guardar dados. Dados podem ser:

  • Números inteiros ou reais
  • Letras ou textos
  • Valores lógicos (booleanos)
  • ... e outros que vocês descobrirão futuramente !

Uma variável possui um identificador, que nada mais é que seu nome. No Scratch as variáveis são criadas e podem ser modificadas com os comandos categorizados em Variáveis (comandos laranjas):


Scratch-var1.png


Variáveis podem ser globais ou locais:

  • Globais: são visíveis e podem ser usadas por qualquer objeto do Scratch.
  • Locais: são visíveis e podem ser usadas somente pelo objeto do Scratch ao qual está vinculada.

Variáveis podem ser usadas em qualquer comando que precise de um valor numérico, como por exemplo o comando para mover um certo número de passos. No exemplo abaixo, um programa faz com que um objeto desenhe um triângulo no palco, sendo que o comprimento do lado do triângulo é informado pelo usuário.

Scratch-var2.png


Variáveis podem ser usadas em expressões aritméticas, que realizam algum cálculo com valores numéricos. No Scratch expressões são criadas combinando-se os blocos contidos em Operadores(blocos verdes-claros):


Scratch-operadores1.png


Usando esses blocos podem-se calcular novos valores usando variáveis ou constantes. Por exemplo, um pequeno programa que desenha um polígono qualquer precisa calcular o ângulo de quina da figura dependendo de sua quantidade de lados:


Scratch-operadores2.png


Usando esses conceitos sobre variáveis e expressões, faça as atividades a seguir.

Pong

Outro jogo clássico chamado Pong mostrava uma bola que refletia em uma parede, voltando e devendo ser interceptada por uma pequena base (que funcionava como raquete) comandada pelo jogador. Se conseguir interceptá-la, a bola é refletida de novo em direção à parede oposta, continuando assim o jogo. Se falhar, o jogo termina. Esse é considerado o primeiro videogame lucrativo a ter sido criado ...

Pong1.jpg


Tente fazer uma versão do Pong usando o Scratch, mas com duas pequenas modificações. Há apenas uma base, que fica no canto inferior do palco. O placar conta quantas vezes a bola tocou o chão (i.e. o jogador falhou em interceptá-la), e se chegar a 0 o jogo termina. A segunda modificação é uma aceleração gradual da bola, que deve deve aumentar de velocidade a cada 5 segundos de jogo.


Para que serão necessárias variáveis nesse jogo ?

O problema da reflexão da bola na barra

Em aula vimos que para fazer a reflexão da bola com a barra deve-se calcular o ângulo de reflexão. No caso da barra estar na horizontal, esse ângulo deve ser calculado assim:

No Scratch isso deve ser feito combinando-se o comando "Aponte para direção" e uma expressão para calcular a nova direção. A direção atual do objeto está contida em sua variável local direção (predefinida nos comandos de Movimentos):


Scratch-reflexao.png


Uma outra versão do Pong

Em uma outra versão ainda encontrada, no canto superior há um conjunto de alvos que devem ser acertados pela bola. Quando se acertarem todos os alvos o jogo termina.


Pong2.jpg

Para casa: um jogo de sinuca

Para exercitar o uso de variáveis vamos criar também um jogo de sinuca. Nesse jogo deve-se usar a bola branca para encaçapar uma outra bola colorida. As bolas se movimentam de forma natural, desacelerando gradualmente devido ao atrito com a mesa. Quando as bolas colidem, suas velocidades e direções se modificam, dependendo de seus valores anteriores e do ângulo de colisão. Quando as bolas batem nos cantos das mesas, devem ser refletidas. Como as bolas predem velocidade gradualmente, dependendo de suas velocidades iniciais e das colisões em algum momento irão fatalmente parar. As caçapas ficam nos dois cantos superiores do palco. Você notará que sem o uso de variáveis, não será possível criar esse jogo, ainda mais se quiser acrescentar mais alguns detalhes.

As tacadas se fazem com um taco representado por uma linha reta, cuja ponta sempre está colada à bola branca. A direção do taco pode ser controlada pelo mouse ou por teclas direita e esquerda. Para fazer uma tacada, deve-se pressionar a tecla seta pra baixo durante um tempo, e então soltá-la. Quanto mais tempo se pressionar essa tecla mais forte será a tacada, e assim mais veloz a bola branca vai disparar. Assim, para realizar tacadas com pouca velocidade deve-se pressionar a tecla seta pra baixo por pouco tempo, e para tacadas mais fortes, em que a bola branca dispara com grande velocidade, deve-se pressionar essa tecla por um tempo maior. Pode-se usar algum objeto e colocá-lo na lateral do palco para informar qual a potência da tacada a ser realizada.

Alguns dados serão necessários para calcular as movimentações das bolas:

  • Peso de cada bola: 100 g
  • Diâmetro das bolas: 8 cm
  • Desaceleração das bolas devido ao atrito com a mesa:
  • Velocidade mínima de tacada: 0 m/s
  • Velocidade máxima de tacada: 4 m/s

30/03: Algoritmos: Usando variáveis, expressões e estruturas de decisão

Estruturas de decisão: blocos de controle usados quando devem-se executar comandos somente se uma determinada condição for verdadeira. Por exemplo, no jogo Pong a bola deve ser refletida se tocar na barra controlada pelo jogador:

Prg-se3.png

Esse tipo de estrutura de decisão se chama Se condição então faça algo. Como indica sua descrição, uma ou mais instruções serão executadas caso a condição seja verdadeira. No exemplo acima, a condição é tocando em barra, e as instruções executados caso isso seja verdade são aponte para a direção 180-direção.


No exemplo do tiro ao helicóptero, inspirado no jogo Space invaders, o jogo deveria terminar quando o tiro acertasse o alvo. Assim, as instruções para término do jogo precisavam estar dentro de uma estrutura Se condição então ..., como mostrado abaixo:


Prg-se1.png


Para ilustrar o uso de Se condição então ..., e o teste de condições em geral, hoje serão feitos dois projetos:

  1. A continuação do jogo Pong, em que a bola deve acertar alvos no topo da tela. Além disso, se a bola tocar no chão mais que 3 vezes o jogador perde.
  2. Um cronômetro a ser visualizado no palco.

31/03: Algoritmos: ainda estruturas de decisão e também de repetição

Por diversas vezes criaram-se programas no Scratch em que o comportamento de um objeto corresponde a repetir uma sequência de comandos. Por exemplo, cada alvo no topo da tela no jogo Pong deve sumir quando for tocado pela bola:

Prg-repeticao1.gif

Assim, ele deve sempre testar se a bola o está tocando, e quando isso acontecer ele deve desaparecer e contabilizar que há uma alvo a menos para ser acertado. Como esse teste deve ser feito repetidamente até que a bola o acerte, torna-se necessário usar uma estrutura de repetição. No caso do Scratch, usou-se o comando Sempre, que faz com que todos os comandos nele contidos sejam executados indefinidamente (no caso, até que a bola toque o alvo). Além dessa parte do programa, o teste se todos os alvos foram acertados também implica a repetição de uma sequência de comandos.

No jogo, a bola deve se movimentar pelo palco, refletindo nas paredes e sendo rebatida pela barra até que todos os alvos tenham sido acertados. Portanto, os comandos que implicam controlar seu movimento devem se repetir seguidamente até que essa condição de término seja alcançada. O comportamento da bola pode desta forma ser descrito simplificadamente pelos comandos mostrados abaixo, em que se usa a variável bananas para indicar quantos alvos faltam para serem acertados. A repetição foi obtida com o comando repita até bananas=0, e dessa forma a repetição se interrompe quando a variável bananas tiver o valor 0.

Prg-repeticao2.gif

Um terceiro exemplo diz respeito à criação de um cronômetro. Uma variável pode ser decrementada uma vez por segundo, até que o cronômetro zere. Um exemplo de como fazer isso segue abaixo:

Prg-repeticao4.png


Como se vê, estruturas de repetição são muito úteis para repetir sequências de comandos. Existem estruturas de repetição incondicionais, que repetem indefinidamente (como o comando sempre do Scratch), e condicionais, que repetem enquanto determinada condição for verdadeira ou até que determinada condição se verifique (ex: comando repita até). Com elas se evita que programas sejam desnecessariamente longos ... na verdade sem elas seriam inviáveis muitos tipos de programas !

Atividade

  1. Adicione o cronômetro na tela do seu jogo Pong. O cronômetro deve ser composto de dois dígitos.
  2. O Pong poderia ficar mais difícil se os alvos fossem móveis e fugissem da bola. Assim, quando sentisse a bola se aproximando um alvo poderia acelerar ou reduzir sua velocidade, visando evitar uma colisão. Modifique então o Pong para que os alvos movam na horizontal de uma lado para o outro, e evitem a colisão com a bola.

06/04: Portugol

Trabalho: deve-se entregar o jogo Pong com o cronômetro, conforme especificado na última aula sobre Scratch.

'Prazo de entrega: 14/04/2011


Os algoritmos que iremos criar serão compostos de:

  • Estruturas de controle: estruturas para controlar a sequência de execução (realização) de algoritmos:
    • Decisão: para realizar testes de forma a decidir que sequências de instruções devem ser executadas
    • Repetição: para repetir sequências de instruções
  • Estruturas de dados: estruturas para representar os dados a serem processados por algoritmos
    • Variáveis e constantes

Portugol

As aulas de Lógica de Programação usarão um software de auxílio ao ensino de algoritmos chamado Portugol, desenvolvido na Escola Superior de Engenharia do Instituto Politécnico de Tomar, em Portugal.

Guia rápido de instalação e utilização do Portugol

Abaixo segue uma breve ajuda de como obtê-lo, instalá-lo e usá-lo. Esse guia assume que você esteja usando o Ubuntu Linux 9.04 ou superior.

  1. Faça o download do Portugol.
  2. Descompacte-o com o seguinte comando:
    tar xzf portugol23.tar.gz
    
  3. Repare que existe agora um subdiretório portugol no diretório onde você o descompactou. Execute o Portugol com o seguinte comando:
    java -jar portugol/Portugol.jar
    
    Obs: você precisará ter Java instalado. Caso não o tenha, execute o comando:
    sudo apt-get install openjdk-6-jre
    
  4. Copie esse arquivo para poder ver fluxogramas coloridos, e grave-o no memso diretório onde está o Portugol.
  5. Veja a ajuda do Portugol, e use-a sempre que tiver dúvidas !


A tela inicial do Portugol segue abaixo, junto com um programa demonstrativo.

Editor-Portugol.png

Exemplos de programas iniciais em Portugol:

  1. Lendo um número e mostrando-o na tela em seguida:
    Inicio
      inteiro x
    
      Escrever "Digite um numero: ",
      Ler X
      Escrever "Numero digitado: ", x
    Fim
    
  2. Lendo dois números, somando-os e mostrando o resultado na tela:
    Inicio
      inteiro x, y
    
      Escrever "Digite um numero: ",
      Ler x
      Escrever "Digite outro numero: ",
      Ler y
      Escrever "Soma = ", x+y
    Fim
    
    O programa abaixo é equivalente:
    Inicio
      inteiro x, y, z
    
      Escrever "Digite um numero: ",
      Ler x
      Escrever "Digite outro numero: ",
      Ler y
      z <- x + y
      Escrever "Soma = ", z
    Fim
    

Atividades

  1. Média de três números: escreva um programa para calcular a média de três números.
  2. Média balanceada de três números: escreva um programa para calcular a média balanceada de três números.
  3. Sequência de Fibonacci: em matemática corresponde aos números:
    1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, ...
    
    ... que pode ser descrita pela relação de recorrência



    ... com valores iniciais e .

    Numerosas formas na natureza apresentam essa sequência, como neste girassol (cujas flores se dispõem em uma espiral):

    Sunflower.jpg Espiral fibonacci.png FibonacciBlocks.png

    Usando o Portugol escreva um programa que mostre os 10 primeiros números dessa sequência.
  4. Distância até o horizonte: escreva um programa que calcule a distância dos seus olhos até o horizonte. Assuma que a Terra é perfeitamente esférica, e que seu raio tem 6.378 km. Considere que você esteja no nível do mar (seus pés tocando a água do mar ;-), e que o horizonte esteja num mar perfeitamente liso. Dica: faça um diagrama desse problema para visualizar sua geometria, e use trigonometria para resolvê-lo.

13/04: Algoritmos

Variáveis e constantes

  • Variável: capaz de guardar um dado a ser usado no algoritmo. Pode ser entendida como uma caixa, onde se coloca um dado e se pode consultá-lo quantas vezes for necessário. O dado pode ser modificado (substituído por outro). Exemplo em Portugol:
    Inicio
      inteiro anos, dias
    
      Escrever "Quantos anos se passaram ? "
      Ler anos
      dias <- anos * 365
      Escrever "... então se passaram ", dias, " dias"
    Fim
    
    Nesse exemplo há duas variáveis: dias e anos
  • Constante: semelhante à variável, porém o dado armazenado não pode ser modificado. Exemplo em Portugol:
    Inicio
      constante inteiro diasPorAno <- 365
      inteiro anos, dias
    
      Escrever "Quantos anos se passaram ? "
      Ler anos
      dias <- anos * diasPorAno
      Escrever "... então se passaram ", dias, " dias"
    Fim
    
    Nesse exemplo há uma constante: diasPorAno


Variáveis e constantes devem ser declaradas antes de serem usadas (algumas poucas linguagens, como Python e Perl, não exigem isto). A declaração consiste do tipo e identificador da variável. O tipo corresponde ao tipo de valor que pode ser guardado, e o identificador é o nome da variável. No exemplo abaixo:

  constante inteiro diasPorAno <- 365
  inteiro anos, dias
Fim

No exemplo acima, há duas variáveis do tipo inteiro, e seus identificadores são dias e anos. O tipo inteiro indica que essas variáveis podem guardar somente números inteiros.

Tipos de variáveis e constantes no Portugol:

Tipo Descrição Exemplo
Inteiro Número inteiro entre -2 147 483 648 e 2 147 483 647 Inteiro x <- 10
Real Número real entre -1.7 E 308 e 1.7 E 308 Real y <- 10.789
Lógico Valor booleano, com valores "Verdadeiro" e "Falso" Logico ok <- Falso
Caracter Um caractere da tabela ASCII Caracter letra <- "A"
Texto Uma sequência de caracteres (ou string) Texto palavra <- "um teste"

A declaração de constantes é semelhante à de variáveis, bastanto prefixá-las com a palavra-chave constante.

Expressões aritméticas

Um conjunto de operações sobre variáveis, constantes e funções numéricas, e que gera um determinado resultado numérico.

Exemplos de expressões aritméticas:

# Uma expressão que calcula quantos segundos existem em um horário do tipo horas, minutos e segundos
3600*horas + 60*minutos + segundos

# Uma expressão que calcula a velocidade instantânea, segundo um MRV
vel_inicial + aceleracao*tempo;

# Uma expressão que calcula o módulo de um vetor bidimensional, que possui coordenadas x e y
raiz(x^2 + y^2)

Os resultados de expressões podem ser mostrados na tela, ou armazenados em variáveis:

# Uma expressão que calcula quantos segundos existem em um horário do tipo horas, minutos e segundos
segundos <- 3600*horas + 60*minutos + segundos

# Uma expressão que calcula a velocidade instantânea, segundo um MRV
escrever 'Velocidade no instante ', tempo, ' = ', vel_inicial + aceleracao*tempo;

# Uma expressão que calcula o módulo de um vetor bidimensional, que possui coordenadas x e y
modulo <- raiz(x^2 + y^2)

Repare que uma expressão fica sempre do lado direito, quando atribuída a uma variável. A expressão é primeiro calculada, e em seguida seu resultado é armazenado na variável:

segundos <- 3600*horas + 60*minutos + segundos

Operadores aritméticos

Expressões aritméticas sao compostas por números e operadores aritméticos:

Obs: para os exemplos abaixo são usadas estas variáveis:

Real x, area, lado
inteiro dias, horas
Operador Descrição Exemplo
+ Adição x <- x + 1
- Subtração x <- x - 1
* Multiplicação x <- x*x*x
/ Divisão dias <- horas / 24
% Módulo (resto de divisão) horas <- horas % 24
^ Potenciação area <- lado^2

Precedência dos operadores (nesta ordem): ^, *, /, %, + e -

A precedência pode ser modificada com o uso de parênteses. Ex:

escrever 1 + 2 * 3
escrever (1 + 2)*3

No Portugol, existem também algumas funções úteis, como a função raiz:

r <- raiz(x^2 + y^2)

O resultado de expressões aritméticas depende dos tipos numéricos das variáveis e constantes:

inicio
  real x
  inteiro y
  inteiro resultadoInteiro
  real resultadoReal
 
  x <- 9
  y <- 9
 
  escrever "O resultado de uma expressão aritmética depende dos tipos das variáveis e constantes\n"
  escrever "usadas na expressão. Se forem todas inteiras, então o resultado será inteiro.\n"
  escrever "Veja este exemplo: \n"
  escrever "Variável inteira y=", y
  escrever "\nExpressão: y/2=", y/2
 
  escrever "\n\nNeste segundo exemplo, repete-se a mesma expressão, porém usando-se uma\n"
  escrever "variável real:\n"
  escrever "Variável real x=", x
  escrever "\nExpressão: x/2=", x/2
 
  x <- 4
  y <- 5
  escrever "\n\nSe as variáveis de diferentes tipos forem combinadas, o resultado da\n"
  escrever "expressão será real:\n"
  escrever "Variável real x=", x, " e inteira y=", y
  escrever "\nExpressão: (x+y)/2=", (x+y)/2
 
  escrever "\n\nNo entanto, se uma expressão tiver um resultado real, mas este for\n"
  escrever "atribuído a uma variável inteira, então apenas a parte inteira será guardada:\n"
  escrever "Variável real x=", x, " e inteira y=", y
  y <- (x+y)/2
  escrever "\nExpressão: y <- (x+y)/2 ... após executada, y=", y
 
fim

Atividade

Para os exercícios abaixo, escreva o algoritmo no Portugol.

  1. Faça um algoritmo que, usando somente duas variáveis, calcule a média de quatro números.
  2. Escreva um algoritmo que calcule as raizes de uma equação de 2o grau.
  3. Um equipamento conta o tempo desde que foi ligado. No entanto, essa contagem é feita em segundos. Faça um algoritmo que converta o valor desse contador para horas, minutos e segundos. Ex: se o contador tiver o valor 43397, o seu programa deve mostrar: 12:03:17.
    inicio
      inteiro h,m,s
    
      escrever "Quantos segundos mostrou o equipamento ? "
      ler s
      
      h <- s /3600
      s <- s % 3600   // s <- s - h*3600
      m <- s /60
      s <- s % 60 // s <- s - m*60
      
      escrever h, ":", m, ":", s
      
    fim
    

14/04: Variáveis e expressões

Continuação ...

Exercícios

  1. Crie um conversor de decimal para binário (limite: 4 bits). Ex.: tendo o número 10 (decimal) de entrada, deve-se obter o número 1010 (binário) de saída.
  2. Escreva um algoritmo que leia o nome, sobrenome e idade de uma pessoa, e escreva na tela (no lugar dos colchetes devem aparecer os valores lidos):
     Nome: [sobrenome, nome]
     Idade: [idade] anos
    
  3. A função exponencial pode ser calculada por uma série de Taylor:

    Faça um algoritmo para calcular o valor desta função.

16/04: Estruturas de decisão

O exemplo abaixo está contido no livro Classification and Regression Trees, de Leo Breiman, Jerome Friedman, Richard Olshen e Charles Stone, editora Chapman & Hall, 1984.

Na Universidade da California, no centro Médico de San Diego, quando um paciente com ataque cardíaco é recebido, dezenove variáveis são medidas ao longo das primeiras 24 horas. Essas incluem pressão sanguínea, idade, e 17 outras variáveis ordenadas e binárias (booleanas) que sumarizam os sintomas médicos considerados importantes indicadores da condição do paciente.

O objetivo de um estudo médico feito entre os anos 70 e 80 foi o desenvolvimento de um método para identificar pacientes de alto risco (que não sobreviverão ao menos 30 dias) com base nos dados obtidos nas primeiras 24 horas. O diagrama abaixo mostra uma regra de classificação que foi produzida nesse estudo. A letra F significa que não há um risco alto, e a letra G quer dizer paciente de alto risco.

Crt-decisao.png

Essa regra classifica os pacientes como F ou G dependendo de respostas do tipo sim/não a no máximo três perguntas. Como seria um algoritmo que a implementasse ?


Algoritmos para resolver problemas como o exemplo acima dependem de se poder expressar a tomada de decisões. Deve ser possível testar condições, como por exemplo "a idade é maior que 62.5 anos ?", e executar instruções dependendo do resultado do teste. Em Lógica de Programação, e em linguagens de programação em geral, isso se faz com estruturas de decisão.

Estruturas de decisão possibilitam que se executem diferentes sequências de instruções de um programa, dependendo de uma condição a ser avaliada. Por exemplo, um jogo poderia armazenar a maior pontuação já obtida, e verificar se foi ultrapassada ao final de cada partida:

  Se pontuacao > recorde então 
    recorde <- pontuação
  FimSe

O exemplo em Portugol acima mostra a estrutura de decisão Se condição entao comandos Fimse. O equivalente em fluxograma é:

Seentao.png

Veja o próximo exemplo:

  Se conceito > 70 entao
    escrever 'Voce esta aprovado'
  senao
    escrever 'Desta vez não deu ... tente de novo !'
  Fimse

O uso de Se condição entao comandos Senao comandos Fimse possibilita que se execute uma sequência de comandos se a condição for verdadeira, e outra sequência se for falsa. Seu equivalente em fluxograma é:

Seentaosenao.png

Para fazer um bom uso de estruturas de decisão deve-se primeiro conseguir identificar as condições a serem avaliadas. Condições são escritas com expressões lógicas, e estas são compostas de operadores lógicos e relacionais aplicados a variáveis e constantes.

Condições

Condições representam os testes que precisam ser feitos com dados do problema. Esses testes são expressados por expressões lógicas, cujos resultados são verdadeiro ou falso. Expressões lógicas são construídas usando-se operadores lógicos e operadores relacionais para comparar e avaliar os valores de variáveis e constantes.

Obs: para os exemplos abaixo são usadas estas variáveis:

Logico correto, multa, aprovado, barato, bombear_agua
Logico descartar, baixo, reprovado, erro, enviado, recebido
inteiro erros, pontuacao, preco, endereco, velocidade
Real faltas, nivel_agua, altura

Operadores relacionais

Operadores relacionais são usados para comparar valores, e estão listados na tabela abaixo. Cada comparação feita com esses operadores forma uma expressão lógica simples. Portanto, o resultado de uma comparação é um valor lógico que pode ser verdadeiro ou falso.

Operador Descrição Exemplo
= Igualdade correto <- (erros = 0)
> Maior multa <- (velocidade > 80)
>= Maior ou igual aprovado <- (pontuacao >= 70)
< Menor barato <- (preco < 100)
<= Menor ou igual bombear_agua <- (nivel_agua <= 0.7)
=/= Diferente descartar <- (endereco =/= 12345)

Operadores lógicos

Operadores lógicos são usados para combinar expressões lógicas simples, criando assim expressões lógicas compostas, e estão listados na tabela abaixo.

Operador Descrição Exemplo
NAO Negação baixo <- NAO (altura > 1.8)
E Conjunção aprovado <- NAO (conceito = "D") E (faltas <= 0.25)
OU Disjunção reprovado <- (conceito = "D") OU (faltas > 0.25)
XOU Disjunção exclusiva erro <- enviado XOU recebido

Precedência dos operadores (nesta ordem): NAO, E, OU e XOU

Lembre que a precedência pode ser modificada com o uso de parênteses.

Atividades

  1. Faça um programa que leia um número e então informe se ele é par ou ímpar.
  2. Um radar de trânsito faz a medição de velocidade de veículos e, dependendo do valor, calcula a multa a ser aplicada. Em uma determinada via esse radar foi configurado da seguinte forma:
    • Se a velocidade for maior que 80 km/h, a multa é de R$ 360.
    • Se a velocidade for maior que 60 km/h, a multa é de R$ 180.
    • Se a velocidade for menor ou igual a 60 km/h, não há multa.

      Escreva um algoritmo que calcule a multa de acordo com a velocidade de um veículo.
  3. Faça um algoritmo que leia três números do teclado, e mostre o maior e menor números.
  4. Escreva um algoritmo que faça o teste de risco de paciente cardíaco, mostrado no início da aula.
  5. Um estudo sobre sensibilidade de pessoas a temperaturas da água identificou que a maioria das pessoas considera fria a água com temperaturas abaixo de 25 graus, morna entre 25 e 30 graus, e quente acima de 30 graus. Escreva um algoritmo que mostre as palavras "fria", "morna" ou "quente" dependendo da temperatura da água que for informada.
  6. Em uma rede de computadores, o firewall restringe o acesso a Internet dependendo do horário e do tipo de usuário que faz o acesso. Os tipos de usuário abaixo têm as seguintes restrições:
    • Funcionario: apenas entre 0:00 e 7:30, entre 18:30 e 0:00, e entre 12:00 e 13:30
    • Financeiro: qualquer horario
    • Diretoria: qualquer horário
      Escreva um algoritmo que informe se um acesso foi permitido, em função do horário e do tipo de usuário.
  7. Modifique o algoritmo acima para adicionar a seguinte restrição:
    • Funcionario: nao pode acessar sites de jornal (ex: www.rbs.com.br)
    • Financeiro: nao pode acessar sites de jornal durante o expediente
    • Diretoria: sem restrições a sites
  8. Faça um algoritmo para fazer a divisão de dois números reais. Antes de dividi-los deve ser feito um teste de validade. Caso não seja possível dividi-los, deve ser mostrada uma mensagem de erro. Se for possível, deve-se mostrar o resultado da divisão.
  9. Faça um jogo de par ou ímpar, em que o jogador aposta contra o computador. O jogador deve digitar um número entre 0 e 5 e optar entre par ou ímpar. O computador deve sortear um número também entre 0 e 5. Se a paridade da soma dos números do jogador e do computador for a mesma que o jogador optou, então ele ganha a partida, senão o computador vence.
  10. Escreva um algoritmo para identificar se há, dentre três palavras lidas do teclado, ao menos duas palavras distintas que pertençam ao conjunto {azul, preto, vermelho}. Exemplos:
    • Se o usuário digitar verde, preto, vermelho, o programa deve mostrar na tela verdadeiro
    • Se o usuário digitar verde, preto, preto, o programa deve mostrar na tela falso
    • Se o usuário digitar azul, preto, azul, o programa deve mostrar na tela verdadeiro
inicio
  texto cor1, cor2, cor3
  inteiro cont <- 0
    
  ler cor1
  ler cor2
  ler cor3
  
  se cor1 = "preto" ou cor2 = "preto" ou cor3 = "preto" entao
    cont <- cont + 1
  fimse

  se cor1 = "azul" ou cor2 = "azul" ou cor3 = "azul" entao
    cont <- cont + 1
  fimse

  se cor1 = "vermelho" ou cor2 = "vermelho" ou cor3 = "vermelho" entao
    cont <- cont + 1
  fimse
        
  se cont > 1 entao
    escrever "verdadeiro"
  senao
    escrever "falso"
  fimse
fim

Fluxogramas

Diagramas de bloco para auxiliar a descrição de algoritmos. Ajudam na compreensão do algoritmo, por poder visualizar o fluxo de execução.


Fluxograma-soma.png Fluxograma para o algoritmo da média de trẽs números.


Blocos de uso mais comum

Bloco Descrição Exemplo
Inicio.png Inicio do fluxograma
Processamento.png Processamento
Entrada.png Entrada de dados (ler do teclado)
Saida.png Saída de dados (mostrar na tela)
Decisao.png Decisão (testar uma condição e bifurcar) Ex-decisao.png
Conector.png Conector (juntar dos ou mais ramos do fluxograma) Ex-conector.png
Fim.png Fim

Obs: Arquivo de configuração das cores do fluxograma do Portugol.

20/04: estruturas de decisão

Há situações em que se precisa fazer um conjunto de comparações, como mostrado abaixo:

// Lê a data no formato numérico dia, mes, ano, e mostra a data no formato
// dia, nome do mês, ano.
Inicio
  inteiro dia, mes, ano
  texto nome_mes

  escrever "Dia: "
  ler dia
  escrever "Mes: "
  ler mes
  escrever "Ano: "
  ler ano

  se mes = 1 entao
    nome_mes <- "Janeiro"
  senao
    se mes = 2 entao
      nome_mes <- "Fevereiro"
    senao
      se mes = 3 entao
        nome_mes <- "Março"
      senao
        se mes = 4 entao
          nome_mes <- "Abril"
        senao
          se mes = 5 entao
            nome_mes <- "Maio"
          senao
            se mes = 6 entao
              nome_mes <- "Junho"
            senao
              se mes = 7 entao
                nome_mes <- "Julho"
              senao
                se mes = 8 entao
                  nome_mes <- "Agosto"
               senao
                  se mes = 9 entao
                    nome_mes <- "Setembro"
                  senao
                    se mes = 10 entao
                      nome_mes <- "Outubro"
                    senao
                      se mes = 11 entao
                        nome_mes <- "Novembro"
                      senao
                        nome_mes <- "Dezembro"
                      fimSe
                    fimSe
                  fimSe
                fimSe
              fimSe
            fimSe
          fimSe
        fimSe
      fimSe
    fimSe
  fimSe

  escrever dia, " de ", nome_mes, " de ", ano
fim

Além de ser trabalhoso esse encadeamento de Se ... entao ... senao, o algoritmo resultante fica pouco legível. Quer dizer, ele fica feio e difícil de entender.

Existe uma estrutura de decisão criada justamente para casos como esse, e que resulta em um algoritmo mais limpo e compreensível:

// Lê a data no formato numérico dia, mes, ano, e mostra a data no formato
// dia, nome do mês, ano.
Inicio
  inteiro dia, mes, ano
  texto nome_mes

  escrever "Dia: "
  ler dia
  escrever "Mes: "
  ler mes
  escrever "Ano: "
  ler ano

  Escolhe mes
    caso 1: 
      nome_mes <- "Janeiro"
    caso 2: 
      nome_mes <- "Fevereiro"
    caso 3: 
      nome_mes <- "Março"
    caso 4: 
      nome_mes <- "Abril"
    caso 5: 
      nome_mes <- "Maio"
    caso 6: 
      nome_mes <- "Junho"
    caso 7: 
      nome_mes <- "Julho"
    caso 8: 
      nome_mes <- "Agosto"
    caso 9: 
      nome_mes <- "Setembro"
    caso 10: 
      nome_mes <- "Outubro"
    caso 11: 
      nome_mes <- "Novembro"
    Defeito: 
      nome_mes <- "Dezembro"
  fimEscolhe

  escrever dia, " de ", nome_mes, " de ", ano
fim

A estrutura de decisão escolhe ... caso tem uma certa flexibilidade. No exemplo abaixo, mostra-se a possibilidade de testar mais de um valor no mesmo caso:

inicio     
  caracter sexo     

  escrever "Qual o seu sexo (f/m):"     
  ler sexo     

  escrever "Olá "     

  escolhe sexo         
    caso "m", "M" :             
      escrever "senhor"         
    caso "f","F" :             
      escrever "senhorita"         
    defeito :             
      escrever "Sexo indefinido"     
  fimescolhe     

  escrever ", benvindo ao portugol" 
fim

Atividades

  1. Faça um algoritmo que converta um número de 1 a 7 para o respectivo dia da semana (ex: 1 = domingo, 2 = 2a feira, e assim por diante).
  2. Faça uma calculadora com as quatro operações aritméticas. Sua calculadora deve ler (nesta ordem) o primeiro número, a operação aritmética (que deve ser informada usando o símbolo da respectiva operação: +, -, * ou /), e depois o segundo número. Ao final, seu algoritmo deve mostrar o resultado, ou uma mensagem de erro se a operação não for possível de realizar (ex: divisão por zero).
  3. A previsão do tempo na costa brasileira pode ser feita de forma aproximada usando-se um barômetro e um termômetro. Uma estimativa com boa chance de acerto se baseia na tabela abaixo:
    Previsao-barometro.png

    Faça um algoritmo que forneça uma estimativa da previsão do tempo usando essa tabela.
  4. Faça um algoritmo que mostre qual o último dia de um determinado mês informado pelo teclado. Caso seja informado o mês 2 (fevereiro), seu algoritmo deve identificar se é ano bissexto (assim o mês tem 29 dias), ou não (mês tem 28 dias). Obs: anos bissextos são dados pelas regras (segundo o calendário Gregoriano):
    1. De 400 em 400 anos é ano bissexto.
    2. De 100 em 100 anos não é ano bissexto.
    3. De 4 em 4 anos é ano bissexto.
      Solução vista em aula: (sem considerar anos bissextos):

27/04: Estruturas de decisão

Exercícios

  1. Um estudo sobre sensibilidade de pessoas a temperaturas da água identificou que a maioria das pessoas considera fria a água com temperaturas abaixo de 25 graus, morna entre 25 e 30 graus, e quente acima de 30 graus. Escreva um algoritmo que mostre as palavras "fria", "morna" ou "quente" dependendo da temperatura da água que for informada.
  2. Faça um algoritmo para fazer a divisão de dois números reais. Antes de dividi-los deve ser feito um teste de validade. Caso não seja possível dividi-los, deve ser mostrada uma mensagem de erro. Se for possível, deve-se mostrar o resultado da divisão.
  3. Escreva um programa que leia cinco números do teclado e mostre os dois maiores números.
  4. Faça um programa que leia o nome de um usuário e sua senha, e em seguida informe se o acesso foi concedido ou negado. Os usuários possíveis de entrar são "joao", "maria" e "zé".
  5. Jogo de Pedra, papel e tesoura: nesse jogo cada jogador faz sua escolha, e vence aquele que escolher um objeto que seja capaz de vencer o outro:
    • Tesoura corta papel
    • Pedra quebra tesoura
    • Papel embrulha a pedra
      Faça um algoritmo que pergunte ao usuário o objeto escolhido, e em seguida faça o computador escolher o seu próprio objeto (dica: use o gerador de números aleatórios visto no jogo do par ou ímpar). Finalmente o algoritmo deve informar o vencedor.

28/04: Estruturas de repetição

Alguns algoritmos vistos anteriormente possuem sequências repetitivas de instruções. Por exemplo, o algoritmo da média de quatro avaliações:

Inicio
  real m1, m2, m3, m4
  real media

  escrever "Avaliação 1:"
  Ler m1
  escrever "Avaliação 2:"
  Ler m2
  escrever "Avaliação 3:"
  Ler m3
  escrever "Avaliação 4:"
  Ler m4

  media <- (m1 + m2 + m3 + m4) / 4

  escrever "Média: ", media
Fim

O algoritmo acima repete quatro vezes a sequência que lê uma nota do teclado. Porém há uma forma de expressar a repetição de sequências de instruções, usando-se o que se chama de estrutura de repetição. A estrutura de repetição enquanto condição faz repete todas as instruções enquanto a condição for verdadeira. A condição é escrita como uma expressão lógica, da mesma forma que na estrutura de decisão se condição então ... senão. Veja como fica o algoritmo acima ao ser reescrito para usar essa estrutura de repetição:

Inicio
  constante inteiro NUMEROS <- 4
  real m
  real media <- 0
  inteiro contador <- 0

  enquanto contador < NUMEROS faz  
    escrever "Avaliação ", contador, ":"
    ler m
    media <- media + m
    contador <- contador + 1
  fimEnquanto

  escrever "Média: ", media/NUMEROS
Fim

Esse algoritmo funciona somente para médias de quatro números. Porém calcular a média de qualquer quantidade de números usa a mesma lógica: ler os números, somá-los e dividir o total pela quantidade de números lidos. Por exemplo, para fazer com que ele calcule a média de 7 números é necessário escrevê-lo assim:

Inicio
  constante inteiro NUMEROS <- 7
  real m
  real media
  inteiro contador <- 0

  enquanto contador < NUMEROS faz  
    escrever "Avaliação ", contador, ":"
    ler m
    media <- media + m
    contador <- contador + 1
  fimEnquanto

  escrever "Média: ", media/NUMEROS
Fim

Note que o algoritmo praticamente não foi modificado, pois somente se alterou o valor da constante NUMEROS.

Esses dois algoritmos podem também ser visualizados como fluxogramas, como mostrado na figura abaixo:

Ex-repeticao.png

A estrutura de repetição junto com a sequência de instruções a ser repetida é comumente chamada de 'laço. No fluxograma acima o laço está destacado em vermelho, e no algoritmo em Portugol o laço aparece em:

  enquanto contador < NUMEROS faz  
    escrever "Avaliação ", contador, ":"
    ler m
    media <- media + m
    contador <- contador + 1
  fimEnquanto

Um outro exemplo ainda mais simples é mostrar na tela uma contagem numérica:

inicio
    inteiro contador
    contador <- 0

    enquanto contador < 10 faz
        escrever contador , " "
        contador <- contador + 1
    fimenquanto
fim

Ao executar esse algoritmo, tem-se como resultado:

0 1 2 3 4 5 6 7 8 9

Seu fluxograma está mostrado a seguir:

Flux-Contagem.png


Repare no uso de uma variável auxiliar contador para controlar a quantidade de repetições. Essa é uma técnica comum para controlar a estrutura de repetição, e já foi usada no exemplo da média. Ela pode também ser combinada com outras condições, como mostrado abaixo:

inicio
    inteiro contador <- 1
    caracter opcao <- "s"
        
    enquanto ((opcao = "s") ou (opcao = "S")) e contador < 11 faz
        escrever contador, "\n"
        contador <- contador + 1
        
        escrever "\nContinuar (S/N) ? "
        ler opcao
    fimenquanto
    
    escrever "Terminou com contador = " , contador
fim

Nesse exemplo se usa um laço para mostrar uma contagem de 1 a 10. Porém há a possibilidade de encerrar o algoritmo. Observe a condição para continuidade do laço: ela é verdadeira somente se contador < 11 e se a variável opcao for igual a "s" ou "S".

Finalmente, apesar de ser comum o uso de contadores para controle do laço, pode-se usar qualquer condição para essa finalidade. Então podem existir laços que não usam contadores para controlar a quantidade de repetições, como no próximo exemplo:

inicio
    constante texto segredo <- "secreto"
    texto senha
    
    ler senha
    enquanto senha =/= segredo faz
        escrever "Voce continua preso ! Digite a senha correta: "
        ler senha
    fimenquanto
    escrever "Voce foi liberado ..."
fim

O fluxograma desse algoritmo segue abaixo:

Flux-Senha.png

Atividades

  1. Escreva um algoritmo que mostre a tabuada de um número fornecido pelo teclado. Esse número deve estar entre 1 e 10.
  2. Aproveite o algoritmo anterior para mostrar a tabuada de todos os números entre 1 e 10.
  3. Modifique o exemplo da média para que a quantidade de números a serem lidos seja previamente informada pelo teclado.
  4. Escreva algoritmos que mostrem as seguintes sequências de números:
    • Números pares menores que 100
    • Números ímpares menores que 100
    • Números pares de 100 até 4 (contagem decrescente)
    • Múltiplos de 3 menores que 100
    • Múltiplos de 4 e múltiplos de 5 menores que 100
    • Múltiplos comuns menores que 1000 de dois números fornecidos pelo teclado (ex: se forem fornecidos 6 e 8, deve aparecer 24, 48, 72, ...)
      inicio
          inteiro n <- 0 , n1 , n2, mmc
          
          escrever "Primeiro numero : "
          ler n1
          escrever "Segundo numero : "
          ler n2
          
          // descobre o mmc de n1 e n2
          se n1 > n2 entao
            mmc <- n1
          senao
            mmc <- n2
          fimse
          
          enquanto mmc % n1 =/= 0 OU mmc % n2 =/= 0 faz
             mmc <- mmc + 1
          fimenquanto
          
          // mostra os multiplos de mmc que sejam <= 1000
          enquanto n <= 1000 faz
              escrever "\n " , n
              n <- n + mmc
          fimenquanto
      fim
      
  5. Escreva um algoritmo para calcular o MMC (Mínimo Múltiplo Comum) de dois números. O MMC de dois números é um número que pode ser dividido por qualquer um deles sem deixar resto. Ex:
    • MMC de 8 e 6 = 24
    • MMC de 3 e 5 = 15
    • MMC de 3 e 27 = 27
  6. Escreva um algoritmo para calcular o MDC (Máximo Divisor Comum) de dois números. O MDC de dois números é um número capaz de dividi-los sem deixar resto. Ex:
    • MDC de 24 e 16 = 8
    • MDC de 5 e 3 = 1
    • MDC de 60 e 150 = 30
      inicio
          inteiro n1 , n2, mdc
       
          escrever "Primeiro numero : "
          ler n1
          escrever "Segundo numero : "
          ler n2
       
          // descobre o mmc de n1 e n2
          se n1 > n2 entao
            mdc <- n2
          senao
            mdc <- n1
          fimse
      
          enquanto mdc > 1 E NAO (n1 % mdc = 0 E n2 % mdc = 0) faz
             mdc <- mdc - 1
          fimenquanto
        
          escrever "MDC=", mdc
      fim
      
  7. Escreva um algoritmo que leia até 10 números do teclado, e informe ao final qual o maior e o menor deles.
  8. Escreva um algoritmo que teste se um número informado pelo teclado é primo.
  9. Aproveite o algoritmo do ítem anterior para mostrar todos os números primos menores que 1000.
  10. Modifique novamente o exemplo da média para que ela funcione para um quantidade de números desconhecida de antemão. Quer dizer, o algoritmo deve ler os números para calcular a média, mas não sabe quantos números existem (e isto não pode ser informado pelo teclado).
  11. Modifique o exemplo da senha para que o usuário tenha somente três tentativas permitidas para digitar a senha correta. Caso ao final as três senhas estejam erradas, o algoritmo deve informar que a conta foi bloqueada.
  12. Usando o algoritmo de teste de número primo, faça um novo algoritmo que fatore um número. Ex: a fatoração do número 15 resulta em 3 e 5 (3 X 5), e a fatoração de 54 resulta em 2, 3, 3 e 3 (2 X 3 X 3 X 3).
  13. Usando estrutura de repetição, escreva um algoritmo que converta um número de decimal para binário. Assuma um número binário com 16 bits.
  14. Faça um algoritmo para descobrir os dois maiores números dentre 6 números lidos do teclado.
  15. Faça um algoritmo para converter um número entre 0 e 16777215 para sua representação em hexadecimal.
  16. Escreva o algoritmo para uma calculadora aritmética (operações +, -, * e /) que lê continuamente do teclado números e operadores. A calculadora deve ler continuamente uma sequência do tipo número operador_aritmético, até que o operador informado seja =, quando então o resultado da conta deve ser mostrado na tela. Ex:
    • 1 + 2 * 5 / 3 = 5
    • 2 * 5 - 1 / 3 = 3

04/05: Estruturas de repetição

Resolução de exercícios (continuando aula anterior).

05/05: Estruturas de repetição

Continuando a resolução de exercícios ...

Uma pequena avaliação

Resolva o seguinte problema em 15 minutos:

Contador de moedas: faça um programa que leia valores de moedas e some as quantidades de tipos de moedas informadas. Por exemplo, se o usuário digitar 25, 50, 25, 5, 10, 5, o programa deve informar: 2 moedas de 5 centavos, 1 moeda de 10 centavos, 2 moedas de 25 centavos, 1 moeda de 50 centavos. São aceitos apenas valores de moedas de 1, 5, 10, 25 e 50 centavos. Seu programa deve ler 10 valores de moedas, e então apresentar o resultado.

inicio
  inteiro m1, m5, m10, m25, m50
  inteiro moeda 
  inteiro n
    
  enquanto n < 10 faz
    escrever "Moeda: "
    ler moeda
    
    escolhe moeda 
      caso 1:
        m1 <- m1 + 1
      caso 5:
        m5 <- m5 + 1
      caso 10:
        m10 <- m10 + 1
      caso 25:
        m25 <- m25 + 1
      caso 50:
        m50 <- m50 + 1
      defeito:
        escrever "Valor invalido ...\n"
        n <- n - 1
    fimescolhe
    n <- n + 1
  fimenquanto

  escrever "Moedas de 1 centavo: ", m1
  escrever "\nMoedas de 5 centavos: ", m5
  escrever "\nMoedas de 10 centavos: ", m10  
  escrever "\nMoedas de 25 centavos: ", m25
  escrever "\nMoedas de 50 centavos: ", m50
fim

11/05: Estruturas de repetição

Variáveis multidimensionais

Em matemática existem matrizes e vetores, que são variáveis multidimensionais. Por exemplo, uma matriz 2 x 2 (2 linhas e 2 colunas) pode ser:

Vetores são matrizes unidimensionais, portanto possuem somente uma linha ou uma coluna:

Cada elemento em uma matriz ou vetor é identificado pela sua posição. Por exemplo, na posição 1, 2 da matriz A acima está o valor 6, e na posição 4 do vetor v está o valor 18. Assim, a matriz A do exemplo pode ser entendida da seguinte forma:

... e o vetor v do exemplo:

Nas linguagens de programação em geral existe um conceito muito parecido, chamado de variáveis multidimensionais ou simplesmente matrizes (arrays em inglês). Para exemplificar, no Portugol se poderiam definir a matriz A e o vetor v:

inicio
  inteiro A[2][2] <- {{1, 6}, {3, 5}}
  inteiro v[5] <- {1, 6, 2, 18, 5}

  escrever "Valor de A[0][0]: ", A[0][0], "\n"
  escrever "Valor de A[0][1]: ", A[0][1], "\n"
  escrever "Valor de A[1][0]: ", A[1][0], "\n"
  escrever "Valor de A[1][1]: ", A[1][1], "\n"

  escrever "Valor de v[0]: ", v[0], "\n"
  escrever "Valor de v[1]: ", v[1], "\n"
  escrever "Valor de v[2]: ", v[2], "\n"
  escrever "Valor de v[3]: ", v[3], "\n"
  escrever "Valor de v[4]: ", v[4], "\n"

fim

A declaração da matriz se faz como uma variável comum, porém indicando-se suas dimensões:

  inteiro A[2][2] <- {{1, 6}, {3, 5}}

Veja que a matriz A foi inicializada na declaração.

O acesso aos elementos da matriz se faz usando-se índices, que funcionam como coordenadas dos elementos que se quer acessar. Os índices iniciam em 0:

  # índice 0,0
  escrever "Valor de A[0][0]: ", A[0][0], "\n"

O exemplo acima pode ser reescrito usando-se estruturas de repetição:

inicio
  inteiro A[2][2] <- {{1, 6}, {3, 5}}
  inteiro v[5] <- {1, 6, 2, 18, 5}
  inteiro i, j

  enquanto i < 2 faz
    j <- 0
    enquanto j < 2 faz
       escrever "Valor do elemento de A na posição ", i, ", ", j, ": ", A[i][j], "\n"
       j <- j + 1
    fimenquanto
    i <- i + 1
  fimenquanto

  i <- 0
  enquanto i < 5 faz
    escrever "valor de v na posição ", i, ": ", v[i], "\n"
    i <- i + 1
  fimenquanto

fim

Como se vê, matrizes e vetores casam perfeitamente com estruturas de repetição, e são úteis para a resolução de inúmeros problemas. Por exemplo, o problema de mostrar o nome do mês a partir do número do mês, feito anteriormente com escolhe ... caso pode ser feito assim com um vetor:

inicio
  texto nome_mes[12] <- {"Janeiro", "Fevereiro", "Março", "Abril", "Maio", "Junho",
                         "Julho", "Agosto", "Setembro", "Outubro", "Novembro",
                         "Dezembro"}
  inteiro dia, mes, ano

  escrever "Dia: "
  ler dia
  escrever "Mes: "
  ler mes
  escrever "Ano: "
  ler ano

  escrever dia, " de ", nome_mes[mes - 1], " de ", ano
fim

Outro problema comum é precisar guardar um conjunto de valores, e depois ordená-los:

inicio
  inteiro v[10]
  inteiro i
  inteiro quantidade

  escrever "Quantos valores serão digitados (máximo = 10) ? "
  ler quantidade

  i <- 0
  enquanto i < quantidade faz
    escrever "valor ", i, ": "
    ler v[i]
    i <- i + 1
  fimenquanto

  // ordena os valores ...

  escrever "valores ordenados: "
  i <- 0
  enquanto i < quantidade
    escrever v[i], " "
    i <- i + 1
  fimenquanto
fim

Atividades

  1. Escreva um algoritmo que leia 5 números do teclado, e depois mostre-os em ordem inversa à que foi digitada.
  2. Escreva um algoritmo que leia dois vetores de 5 números, e depois mostre se os vetores são iguais.
  3. Escreva um algoritmo que leia um palavra do teclado e depois procure-a numa lista de palavras preexistente. Essa lista deve ser implementada usando um vetor.
  4. Escreva um algoritmo que leia 5 números, e mostre-os em ordem crescente.
  5. Modifique o algoritmo anterior para mostrá-los em ordem decrescente.
  6. Em um jogo de bingo devem-se contar quantos números de uma aposta foram sorteados no bingo. Faça um algoritmo que, dados os números sorteados e uma aposta, conta quantos números apostados foram sorteados.

12/05: Estruturas de repetição

Para variavel de inicio ate fim passo incremento

Há casos em que se deseja repetir uma parte de um algoritmo certo número de vezes. Para esses casos há uma estrutura mais prática que enquanto condição faz:

inicio
  inteiro i
  inteiro v[5]

  escrever "Digite 5 números: \n"

  para i de 0 ate 4 passo 1
    escrever "Numero ", i, ": "
    ler v[i]
  proximo

  escrever "\nOs numeros em ordem inversa são:\n\n"

  para i de 4 ate 0 passo -1
    escrever "Numero ", i, ": ", v[i], "\n"
  proximo

fim

Atividades

  1. Escreva o algoritmo para comparar dois vetores, porém usando a estrutura para.
  2. Escreva um algoritmo para procurar se um vetor menor (com menos valores) está contido em um vetor maior. Caso afirmativo, mostre a partir de que posição ele aparece. Assuma vetores de números inteiros.
  3. Modifique o algoritmo acima para mostrar todas as ocorrências do vetor menor dentro do maior.
  4. Modifique o algoritmo do anterior para remover todas as ocorrências do vetor menor dentro do maior.
  5. Resolva o problema do bingo usando a estrutura para

18/05: Revisão

...exercícios

Resolver a avaliação de 2010-2:

1) Contador de moedas: faça um programa que leia valores de moedas e some as quantidades de tipos de moedas informadas. Por exemplo, se o usuário digitar 25, 50, 25, 5, 10, 5, o programa deve informar: 2 moedas de 5 centavos, 1 moeda de 10 centavos, 2 moedas de 25 centavos, 1 moeda de 50 centavos. São aceitos apenas valores de moedas de 1, 5, 10, 25 e 50 centavos. Seu programa deve ler 10 valores de moedas, e então apresentar o resultado.

2) Calculadora de troco: escreva um programa que calcule o troco a ser devolvido a um cliente. O troco deve ser composto de notas de 50, 20, 10, 5, 2 ou 1 real, e também moedas de 1, 5, 10, 25 ou 50 centavos. Dê preferência ao uso de notas e moedas de maior valor. Por exemplo, se o troco a ser devolvido for R$ 17,75, seu programa deve informar 1 nota de R$ 10, 1 nota de R$ 5, 1 nota de R$ 2, 1 moeda de R$ 0,50, 1 moeda de R$ 0,25.

3) Modificação de senha: Para modificar uma senha deve-se primeiro fornecer a senha atual, e então a nova senha. É necessário escrever duas vezes a nova senha para confirmá-la. Escreva um algoritmo que modifique uma senha predefinida (no seu programa ela pode estar guardada em uma variável), seguindo essa regra de mudança de senha.

4) Nota de uma prova olímpica: um atleta de saltos ornamentais tem seu salto avaliado por 6 juízes. Após descartar a maior e a menor nota, calcula-se a média aritmética das notas dadas. Faça um programa que calcule a nota de um atleta.

... mais algumas questões interessantes:

5) Filtro: Um programa possui 10 números inteiros em um vetor. No entanto, para a próxima etapa de processamento apenas os números entre 3 e 8 são válidos. Escreva um algoritmo que remova os números inválidos do vetor. Ao final o vetor deve conter somente os números válidos.

6) Tabuleiro: Escreva um programa que mostre o conteúdo de uma matriz 4 x 4 na tela. Essa matriz contém valores inteiros que podem ser positivos ou negativos. Ao mostrar cada valor da matriz, deve-se seguir a seguinte regra:

  • Valor negativo: deve ser mostrado um espaço em branco
  • Valor entre 1 e 8: mostrar o próprio valor
  • Valor acima de 8: mostrar o caractere H

Além disso, a matriz deve ser mostrada com uma grade. Por exemplo, a matriz com conteúdo:

... que em Portugol seria declarada assim:

inteiro A <- {{1, 6, 10, -1}, {3, 5, -1, -1}, 
              {10, 4, -1, 5}, {3, -1, 1, -1}}

... deveria ser mostrada da seguinte forma:

..| 1 | 2 | 3 | 4 |
-------------------
A | 1 | 6 | H |   |
-------------------
B | 3 | 5 |   |   |
-------------------
C | H | 4 |   | 5 |
-------------------
D | 3 |   | 1 |   |
-------------------

Quer dizer, as colunas devem ser identificadas por seus números, e as linhas devem ser identificadas pelas letras A, B,C, D.

Linguagem C: Projeto final

19/05: Introdução à linguagem C

Obs: durante as aulas usaremos o NetBeans, um Ambiente Integrado de Desenvolvimento (IDE - Integrated Development Environment). Um IDE é um programa que auxilia o programador. Ele integra um editor de programas, um gerenciador de projetos, compilador e um depurador (debugger).

Para instalar o Netbeans:

  1. Faça o download do instalador. Salve-o em algum subdiretório.
  2. Abrindo um terminal, entre no subdiretório onde está o instalador e execute esse comando:
    bash netbeans-6.8-ml-cpp-linux.sh
    
    • Caso o instalador falhe porque não encontrou a JVM (Máquina Virtual Java), instale-a com esse comando:
      sudo apt-get install -y sun-java6-jdk
      
  3. Aceite as opções de instalação sugeridas pelo instalador.
  4. Ao final da instalação, o Netbeans 6.8 estará acessível pelo menu Aplicativos -> Programação.
  5. Sempre que for escrever um novo programa com o Netbeans, crie um novo projeto (ver menu Arquivo->Novo Projeto). Selecione um projeto do tipo "Aplicativo C/C++".

Compilando o primeiro programa

Obs: para compilar um programa você deve salvá-lo em um arquivo com extensão .c. Por exemplo, ao editar o exemplo abaixo, você pode gravá-lo no arquivo hello.c. Em seguida você deve compilá-lo usando o seguinte comando:

gcc hello.c -o hello

Para executá-lo, faça assim:

./hello

O arquivo que contém o programa em linguagem C se chama arquivo de código-fonte. O arquivo que contém o programa compilado se chama arquivo de código-objeto.


  • O clássico Hello World!
#include <stdio.h>

int main(int argc, char *argv[])
{
	printf("Alô mundo!\n");
}
  • Mostrando mensagens de na tela: puts e printf:
    #include <stdio.h>
    
    int main() {
      int n;
    
      n = 5;
      
      puts("Demonstração de puts e printf");
    
      printf("Valor de n: %d\n", n);
    
      n = n + 1;
    
      printf("Novo valor de n: %d\n", n);
    
      return 0;
    }
    
  • Lendo dados do teclado: scanf
    #include <stdio.h>
    
    int main() {
      int n;
    
      printf("Digite um número inteiro: ");
    
      scanf("%d", &n);
    
      printf("Valor digitado foi %d\n", n);
    
      return 0;
    }
    

Tipos de dados

Portugol C Exemplo
inteiro int int x;
caracter char char letra;
real float ou double float pi = 3.1416;
texto char * ou vetor de char char * mensagem = "Hello world";
char palavra[16];
logico qualquer tipo (valor 0 = Falso, qualquer outro valor = Verdadeiro) int ok = 1;
char teste = 0;


Comandos/funções e Estruturas de controle

Portugol C Exemplo
inteiro n, m

escrever "Ola, mundo!\n"
escrever "valor de n: ", n, "\n"
escrever "valor de n: ", n, ", e valor de x: ", x, "\n"
int n, m;

printf("Ola, mundo!\n");
printf("valor de n: %d\n", n);
printf("valor de n: %d, e valor de x: %d\n", n, x);
inteiro n

ler n
int n;

scanf("%d", &n);
se condição então
//comandos
fimse
if (condição) {
//comandos
}
se condição então
  //comandos
senão
  //comandos
fimse
if (condição) {
 //comandos
} else {
 //comandos
}
escolhe expressão
  caso valor1:  
    //comandos
  caso valor2:
    //comandos
  defeito:
    //comandos
fimescolhe
switch (expressão) {
  case valor1:
    //comandos
  case valor2:
    //comandos
  default:
    //comandos
}
enquanto condição faz
//comandos
fimenquanto
while (condição) {
  //comandos
}
para variavel de inicio ate fim passo incremento
//comandos
proximo
for (variavel=inicio; variavel <= fim; variavel++) {
//comandos
}

Atividades

  • Traduza para C os seguintes algoritmos Portugol:
    1. Inicio
        inteiro x, y
       
        Escrever "Digite um numero: ",
        Ler x
        Escrever "Digite outro numero: ",
        Ler y
        Escrever "Soma = ", x+y
      Fim
      
    2. Inicio
        inteiro x, y, z
       
        Escrever "Digite um numero: ",
        Ler x
        Escrever "Digite outro numero: ",
        Ler y
        z <- x + y
        Escrever "Soma = ", z
      Fim
      
    3. Inicio
        Inteiro n1, n2, n3, r
       
        Escrever "Primeiro numero: "
        ler n1
        Escrever "Segundo numero: "
        ler n2
        Escrever "Terceiro numero: "
        ler n3
       
        r <- (n1 + n2 + n3) /3
       
        Escrever "Media=", r
      Fim
      
    4. Inicio
        inteiro anos, dias
       
        Escrever "Quantos anos se passaram ? "
        Ler anos
        dias <- anos * 365
        Escrever "... então se passaram ", dias, " dias"
      Fim
      
    5. Inicio
        constante inteiro diasPorAno <- 365
        inteiro anos, dias
       
        Escrever "Quantos anos se passaram ? "
        Ler anos
        dias <- anos * diasPorAno
        Escrever "... então se passaram ", dias, " dias"
      Fim
      
    6. inicio
        real massa
        real forca
        real aceleracao
        constante real g <- 9.8
        constante real ac <- 0.01
        
        escrever "força: "
        ler forca
        
        escrever "massa: "
        ler massa
        
        aceleracao <- forca/massa - ac*massa*g
        
        escrever "aceleracao=", aceleracao, " m/s2"
        
      fim
      
    7. inicio
        real a, b, c
        real delta
        real x1, x2
        
        escrever "Forneça os coeficientes da equação de 2o grau (formato: ax^2 + bx + c):\n"
        escrever "a="
        ler a
        escrever "b="
        ler b
        escrever "c="
        ler c
        
        delta <- b^2 - 4*a*c
        x1 <- (-b + delta^0.5)/(2*a)
        x2 <- (-b - delta^0.5)/(2*a)
        
        escrever "1a raiz=", x1
        escrever "\n2a raiz=", x2  
      fim
      
    8. inicio
            real x1, x2, x3, x4, x5
            real media
            real desvioPadrao
            constante inteiro N <- 5
            
            // Ler os cinco valores pelo teclado
            ler x1
            ler x2
            ler x3
            ler x4
            ler x5
            
            // Calcular a media
            media <- (x1 + x2 + x3 + x4 + x5) / N
            
            // Calcular o desvio padrao
            desvioPadrao <- (x1 - media)^2 + (x2 - media)^2 + (x3 - media)^2 + (x4 - media)^2 + (x5 - media)^2
            desvioPadrao <- (desvioPadrao / (N-1))^0.5
            
            escrever "Media=", media
            escrever "\nDesvio padrao=", desvioPadrao
      fim
      
    9. inicio
            real renda
            real irpf
            
            escrever "Informe sua renda: "
            ler renda
            
            se renda < 1372.81 entao
              irpf <- 0
            senao 
              se renda < 2743.25 entao
                irpf <- (renda - 205.92)*0.15 
              senao
                irpf <- (renda - 548.82)*0.275
              fimSe
            fimSe
            
            escrever "Imposto devido: ", irpf  
      fim
      
    10. inicio
          inteiro dividendo
          inteiro divisor
          inteiro resto , quociente
      
          escrever "Dividendo: "
          ler dividendo
          escrever "Divisor: "
          ler divisor
      
          se divisor = 0 entao
              escrever "Nao pode dividir: divisor = 0 !!!"
          senao
              resto <- dividendo % divisor
              se resto = 0 entao
                  quociente <- dividendo / divisor
                  escrever dividendo , " / " , divisor , " = " , quociente
              senao
                  escrever "Nao pode fazer divisao inteira"
                  escrever " (resto = " , resto , ")"
              fimse
          fimse
      fim
      
    11. inicio
          inteiro termometro , barometro , tempo
      
          escrever "Qual a condição do termômetro: \n"
          escrever "Digite 1 para baixando , 2 para estacionário e 3 para subindo. \n"
          ler termometro
      
          escrever "Informe a condição do barômetro: \n"
          escrever "Digite 1 para baixando , 2 para estacionário e 3 para subindo. \n"
          ler barometro
      
          tempo <- termometro*10 + barometro
      
          escolhe tempo
              caso 11:
                  escrever "Chuvas abundantes e ventos de sul a sudoeste fortes"
              caso 12:
                  escrever "Chuva Provavel , ventos de sul a sudeste"
              caso 13:
                  escrever "Tempos Bons , ventos de sul a sudeste"
              caso 21:
                  escrever "Frente quente com chuva provavel"
              caso 22:
                  escrever "Tempo Incerto , ventos variaveis"
              caso 23:
                  escrever "Tempos Bons , ventos do leste frescos"
              caso 31:
                  escrever " Tempo instavel , aproximaçao de frente"
              caso 32:
                  escrever "Tempo Mudando para bom , ventos de leste"
              caso 33:
                  escrever "Tempos Bons , ventos quentes e secos"
              defeito:
                  escrever "Utilize somente os algorismos de 1 a 3 para indicar as condiçoes do equipamentos"
          fimescolhe
      fim
      
    12. inicio
          // coeficientes do polinomio  [ax^2 + bx + c = 0 ]
          real a , b , c
          
          escrever "Forneça os coeficientes da equação de 2o grau:\n"
          escrever "a="
          ler a
          escrever "b="
          ler b
          escrever "c="
          ler c
          
          // equação do tipo [ bx + c = 0 ]
          se a = 0 entao
              escrever " não é uma equação de 2o grau !!!"
          senao
              // calcular o delta => interior da raiz
              real delta
              
              delta <- b ^ 2 - 4 * a * c
              
              // não existem raizes  reais de números negativos
              se delta < 0 entao
                  escrever " não tem raizes reais"
              senao
                  // -----------  raiz dupla  ----------------
                  se delta = 0 entao
                      real x1
                      x1 <- -b / 2 * a
                      escrever "\nraiz dupla : " , x1
                  senao
                      // - ---------- duas raizes ---------------
                      real x1 , x2
                      x1 <- ( -b + raiz ( delta ) ) / 2 * a
                      x2 <- ( -b - raiz ( delta ) ) / 2 * a
                      escrever "\nraiz x1 : " , x1
                      escrever "\nraiz x2 : " , x2
                  fimse//raiz dupla
              fimse// delta >0
          fimse// a <> 0
      fim
      
    13. inicio
          inteiro num, bit
          inteiro base
          
          escrever "Este algoritmo converte um número inteiro para sua representação binária.\n"
          Escrever "O número deve estar entre 0 e 131071, e a representação binária\n"
          escrever "terá 17 bits\n\n"
          escrever "Digite o numero a ser convertido para binário: "
          ler num
      
          base <- 65536
          enquanto base > 0 faz
              bit <- ( num / base ) % 2
              escrever bit, " " 
              base <- base / 2
          fimenquanto
      fim
      
    14. inicio
          inteiro n , fat
          ler n
          fat <- 1
          enquanto n > 1 faz
             fat <- fat * n
             n <- n - 1         
          fimenquanto
          
          escrever "Fatorial=" , fat
      fim
      
    15. inicio
          inteiro valor , menor , contador
          ler menor
          contador <- 9
          enquanto contador > 0 faz
              ler valor
              se valor < menor entao
                  menor <- valor
              fimse
              contador <- contador - 1
          fimenquanto
          escrever "menor valor = ", menor
      fim
      
    16. inicio
          inteiro numero , n , resto <- 1
          escrever "Forneçaa um número: "
          ler numero
          n <- 2
          enquanto n <= numero / 2 e resto =/= 0 faz
              resto <- numero % n
              escrever "n=" , n , ": resto=" , resto , "\n"
              n <- n + 1
          fimenquanto
          
          se resto = 0 entao
              escrever "nao primo: divisivel por " , n - 1
          senao
              escrever "primo"
          fimse
      fim
      
    17. // Le 5 valores e identifica os dois maiores.
      inicio
          inteiro valor , maior1 , maior2 , contador
          
          ler valor
          maior1 <- valor
          
          ler valor
          se valor > maior1 entao
            maior2 <- maior1
            maior1 <- valor
          senao
            maior2 <- valor
          fimse
      
          contador <- 3
          enquanto contador > 0 faz
              ler valor
              se valor > maior1 entao
                  maior2 <- maior1
                  maior1 <- valor
              senao
                  se valor > maior2 entao
                      maior2 <- valor
                  fimse
              fimse
              contador <- contador - 1
          fimenquanto
      
          escrever "maior valor = " , maior1
          escrever "\nsegundo maior valor = " , maior2
      fim
      

25/05: Avaliação

No laboratório ...

Prova resolvida

1) Um programa em uma estação meteorológica converte os valores lidos de um higrômetro para um indicativo de umidade do ar. A tabela de conversão segue abaixo:

Valor do higrômetro Indicativo de umidade
0 a 0.3 muito baixa
0.3 a 0.5 baixa
0.5 a 0.8 normal
0.8 a 1 alta
1 precipitação

Escreva esse programa, que deve simular a leitura do higrômetro pelo teclado e mostrar o indicativo de umidade na tela.

inicio
    real h
    
    escrever " digite um valor de 0 a 1:  " , 
    ler h
    
    se h = 1 entao
        escrever "chuva" ,
    senao
        se h <= 0.3 entao
            escrever "umidade muito baixa" ,
        senao
            se h <= 0.5 entao
                escrever "umidade baixa" ,
            senao
                se h <= 0.8 entao
                    escrever "umidade normal"
                senao
                    se h < 1 entao
                        escrever "umidade alta"
                        
                    fimse
                fimse
            fimse
        fimse
    fimse
fim

2) Um programa possui o seguinte vetor de inteiros guardado em memória:

{10,12,7,4,5,9,2,3,1,3,4,2,2,9}

Esse programa deve ler uma sequência de 4 números pelo teclado, e procurá-la dentro do vetor que está em memória. Se a sequência for encontrada, a posição em que ela inicia dentro do vetor deve ser mostrada.

inicio
  inteiro numeros[14] <- {10,12,7,4,5,9,2,3,1,3,4,2,2,9}
  inteiro v[4]
  inteiro i, j
  
  Escrever "Digite 4 numeros inteiros:"
  para i de 0 ate 3 passo 1
    ler v[i]
  proximo
  
  para j de 0 ate 10 passo 1
    i <- 0
    enquanto i < 4 E v[i] = numeros[j+i] faz
      i <- i + 1
    fimenquanto
    se i = 4 entao
      escrever "Encontrou na posicao ", j
      fim
    fimse
  proximo
  escrever "Nao encontrou em nenhuma posicao"
fim

3) Um número primo é um número divisível somente por 1 ou por si mesmo. Quer dizer, se tentar dividi-lo por qualquer valor maior que 1 e menor que esse número, o resto será diferente de zero. Exemplos de números primos são 2, 3, 5, 7 e 11. Escreva um programa que leia um número pelo teclado e informe se ele é primo.

inicio
    inteiro numero , n

    escrever "Forneça um número: "
    ler numero

    n <- 2   
    enquanto n <= numero / 2 E resto =/= 0 faz       
        resto <- numero % n
        n <- n + 1
    fimenquanto
    
    se resto = 0 entao
        escrever "nao primo: divisivel por " , n - 1
    senao
        escrever "primo"
    fimse
fim

... uma versão com uma pequena melhoria:

inicio
    inteiro numero, n, resto

    escrever "Forneça um número: "
    ler numero

    
    resto <- numero % 2
    se resto =/= 0 entao
      n <- 1
      enquanto n <= numero / 2 E resto =/= 0 faz       
          n <- n + 2
          resto <- numero % n
      fimenquanto
      
      se resto = 0 entao
          escrever "nao primo: divisivel por " , n
      senao
          escrever "primo"
      fimse
    senao
      escrever "nao primo: divisivel por 2"
    fimse
fim

4) Jogo de Pedra, papel e tesoura: nesse jogo cada jogador faz sua escolha, e vence aquele que escolher um objeto que seja capaz de vencer o outro:

* Tesoura corta papel
* Pedra quebra tesoura
* Papel embrulha a pedra

Faça um algoritmo que pergunte ao usuário o objeto escolhido, e em seguida faça o computador escolher o seu próprio objeto (dica: use o gerador de números aleatórios visto no jogo do par ou ímpar). Ao final o algoritmo deve informar o vencedor.

inicio
    inteiro lancecomputador , lancejogador
    logico jogadorvenceu
    
    escrever "Escolha papel (1) , pedra (2) ou tesoura (3): "
    ler lancejogador
    se lancejogador > 3 ou lancejogador < 1 entao
        escrever "Lance inválido !!! (deve digitar um número entre 1 e 3)\n\n"
    senao
        lancecomputador <- 1 + 2 * aleatorio ( )
        escrever "Computador escolheu: " , lancecomputador , "\n"
        se lancejogador = lancecomputador entao
            escrever "Empate !\n\n"
        senao
          jogadorvenceu <- falso
          escolhe lancejogador
              caso 1:
                  se lancecomputador = 2 entao
                      jogadorvenceu <- verdadeiro
                  fimse
              caso 2:
                  se lancecomputador = 3 entao
                      jogadorvenceu <- verdadeiro
                  fimse
              caso 3:
                  se lancecomputador = 1 entao
                      jogadorvenceu <- verdadeiro
                  fimse
          fimescolhe
          escrever "Vencedor: "
          se jogadorvenceu entao
              escrever "jogador\n\n"
          senao
              escrever "computador\n\n"
          fimse
      fimse
    fimse
fim

... uma outra solução:

inicio

   inteiro lancecomputador , lancejogador
   logico jogadorvenceu
   texto vencedor , opcao
   
   escrever "Jogo de Papel , Pedra e Tesoura\n\n"
   escrever "Escolha papel (1) , pedra (2) ou tesoura (3): "
   ler lancejogador
   se lancejogador > 3 ou lancejogador < 1 entao
       escrever "Lance inválido !!! (deve digitar um número entre 1 e 3)\n\n"
   senao
       lancecomputador <- 1 + 2 * aleatorio ( )
       escrever "Computador escolheu: " , lancecomputador , "\n"
       se lancejogador = lancecomputador entao
           escrever "Empate !\n\n"
       senao
           escrever "Vencedor: "
           // repare em como se determina o vencedor nesta versao do jogo: a condicao abaixo
           // é verdadeira sempre que o lance do jogador estiver uma unidade atrás do computador:
           //
           // Jogador     Computador
           //    1             2
           //    2             3
           //    3             1 (nesta última preciso considerar que a contagem é circular)
               
           se (lanceJogador%3 + 1) = lanceComputador entao
               escrever "jogador\n\n"
           senao
               escrever "computador\n\n"
           fimse
       fimse
   fimse

fim </syntaxhighlight>

5) Um programa somente pode ser usado por usuários autorizados. Os usuários e seuas senhas estão armazenados em uma tabela dentro do próprio programa. Escreva o algoritmo desse programa que pede o usuário e senha pelo teclado, consulta a tabela de usuários e depois informa se o acesso foi concedido ou negado. Os usuários e respectivas senhas estão mostrados abaixo:

Usuário Senha
joao tainha
maria pirao
maneca onibus
bilica bilro

Obs: essa tabela pode ser modificada futuramente, então o algoritmo deve conseguir trabalhar com quaisquer usuários e senhas que ali sejam armazenados. Isso é, mesmo que essa tabela tenha seu conteúdo alterado, o algoritmo não pode ser modificado.

inicio
  texto usuarios <- {"joao", "maria", "maneca", "bilica"}
  texto senhas <- {"tainha", "pirao", "onibus", "bilro"}
  texto login, umaSenha
  inteiro i
  logico OK <- falso
  
  escrever "Usuario:"
  ler login
  
  escrever "Senha:"
  ler umaSenha
  
  enquanto i < 4 E nao OK faz
    ok <- usuarios[i] = login
    i <- i + 1
  fimenquanto

  se ok entao
    ok <- senhas[i] = umaSenha
  fimse
  
  se ok entao
    escrever "acesso concedido"
  senao
    escrever "acesso negado"
  fimse
  
fim

Conceitos

Legenda:

  • T: questão correta
  • P: questão parcialmente correta
  • N: questão incorreta ou em branco
Aluno Conceito Questão 1 Questão 2 Questão 3 Questão 4 Questão 5
Alfredo D T (mas não da forma mais eficiente) N N N N
Ângelo D T (mas não da forma mais eficiente) N P N N
Beatriz D N N P (primos somente menores que 12) N N
Bruno da Silva D N (erros de sintaxe) N T N (copiado de um exemplo do professor) N
Bruno D N N N N N
Caroline D T N N N N
Danilo B T (mas não da forma mais eficiente) T (mas não da forma mais eficiente) N (idêntico ao do Gabriel) T T (mas não da forma mais eficiente)
Dayze D N N N N N
Fabiana C T (mas não da forma mais eficiente) P N T N
Felipe C T N N P (computador deveria jogar) P (funciona só pra 4 contas)
Gabriel D T (mas não da forma mais eficiente) N N (idêntico ao do Danilo) N P (funciona só pra 4 contas)
Grazielle D N N N N N
Jayson D N N N N P (funciona só pra 4 contas)
Juliano C T (mas não da forma mais eficiente) N N T P (funciona só pra 4 contas)
Leandro D T (mas não da forma mais eficiente) N N N N
Leonardo D P (condições trocadas) N N P (não indica o vencedor) N

26/05: Começo do projeto

Para referência: apostila online sobre linguagem C.