sexta-feira, 25 de novembro de 2011

Teste 3 (Turma 7)

O novo teste colocava questões de natureza teórica, teórico-prática e prática. Muitos aluno@s continuam com problemas sérios nestes diversos aspectos. Como tenho afirmado várias vezes, só há uma maneira de aprender a programar que é programar. Mesmo a errar se aprende. Mas não é durante os testes que se aprende... Dito isto vamos às perguntas.

Pergunta 1

O conceito de aliasing foi várias vezes referido nas aulas. Na sua essências significa a atribuição de dois ou mais nomes a um mesmo objecto. Um exemplo simples

01.>>> a = [1,2,3]
02.>>> b = a
03.>>> b
04.[1, 2, 3]
05.>>> id(a)
06.4412212648
07.>>> id(b)
08.4412212648
09.>>>

a e b são nomes para o mesmo objecto. Um problema colocado por este mecanismo é a possibilidade, quando os objectos são mutáveis, ao alterarmos um objecto através de um dos seus nomes, todos os outros acompanham a mudança.
1.>>> a[1] = 4
2.>>> a
3.[1, 4, 3]
4.>>> b
5.[1, 4, 3]
6.>>>


Pergunta 2

Eis o programa errado.
1.def retira_dup(x):
2.    for i in range(len(x)):
3.        if x[i] in x[i+1:]:
4.            x[i+1:].remove(x[i])
5.    return x


Comecemos pelo tipo de objecto. Tem que ser uma sequência, devido à operação de fatiamento. De entre as sequências possíveis (lista de caracteres, tuplos, listas) terá que ser um lista pois trata-se do método remove.

Agora os erros. A ideia do programa é a verificar se o elemento na posiçãoi existe na parte da lista a partir de i+1. Se existe, então estamos perante uma repetição, pelo que precisamos retirar todas as suas ocorrências. Mas o método remove só tira uma. Logo aqui temos um problema. Por outro lado, ao retirar elementos estamos a alterar a lista que fica mais pequena e pode acontecer que por isso isso tome valores fora da lista e isso vai gerar um erro. Uma forma de concertar as coisas é dada no programa abaixo.
1.def retira_dup_good(x):
2.    res = []
3.    for i in range(len(x)):
4.        if x[i] not in x[i+1:]:
5.            res.append(x[i])
6.    return res


Usamos a ideia ciclo-contador-acumulador.

Problema 3

A questão colocada pode ser resolvida procurando saber se é possível fazer a ligação entre todos os vértices do grafo que aparecem no caminho. Mal falhe um caso, devolve-se falso.
1.def percurso(grafo, caminho):
2.    for ind in range(len(caminho)-1):
3.        if  caminho[ind+1] not in grafo.get(caminho[ind]):
4.            return False
5.    return True


Como se pode ver o problema resolve-se com as operações e métodos mais comuns dos dicionários. Caso não tenha conseguido resolver na aula, estude bem esta solução.

Sem comentários:

Enviar um comentário