sábado, 7 de janeiro de 2017

Teste 3 - TP1

Problema 2

Num dicionários a diferentes chaves podemos ter associado o mesmo valor. O problema de calcular qual o valor mais frequente pode ser resolvido de forma simples do seguinte modo:
01.def moda(dicio):
02.    # inverte dicio
03.    novo_dicio = {}
04.    for c,v in dicio.items():
05.        novo_dicio[v] = novo_dicio.get(v,[]) + [c]
06.    # passa a lista ordenada
07.    lista_items = list(novo_dicio.items())
08.    mais_freq = (0,[])
09.    for val,lst in lista_items:
10.        if len(lst) > len(mais_freq[1]):
11.            mais_freq = (val,lst)
12.    # devolve o mais valor mais frequente
13.    return mais_freq   
Como os comentários indicam, a estratégia de solução passa por inverter o dicionário, converter para uma lista e depois calcular o elemento, i.e. o par (valor, lista das chaves com esse valor), mais frequente. Para os pythónicos apresentamos outra solução que recorre a funções anónimas:
01.def moda_b(dicio):
02.    # inverte dicio
03.    novo_dicio = {}
04.    for c,v in dicio.items():
05.        novo_dicio[v] = novo_dicio.get(v,[]) + [c]
06.    # passa a lista ordenada
07.    lista_items = list(novo_dicio.items())
08.    lista_items.sort(key=lambda x: len(x[1]),reverse=True)
09.    # devolve o mais valor mais frequente
10.    return lista_items[0]
A função anónima (lambda) é usada para o ordenamento ser feito de acordo com o tamanho do elemento na posição 1.

Problema 3

O problema envolvia um ficheiro em que cada linha é formado por um nome e números (>= 3). Pretende-se criar um novo ficheiro com o nome e a média dos números depois de retirar o menor e o maior.

Uma solução mágica:
01.def fich_media(fich_entrada,fich_saida):
02.    # modificar linha a linha
03.    # abre ficheiros
04.    f_in = open(fich_entrada,'r',encoding='utf8')
05.    f_out = open(fich_saida,'w',encoding='utf8')
06.     
07.    # trata por linha
08.    for linha in f_in:
09.        # escolhe numeros
10.        linha = linha.strip().split()
11.        nome = linha[0]
12.        numeros = [ int(num) for num in linha[1:]]
13.        numeros.sort()
14.         
15.        # calcula média
16.        media = sum(numeros[1:-1])/(len(numeros)-2)
17.        # escreve nova linha
18.        f_out.write(nome + str(media) + '\n')
19.    # fecha ficheiros
20.    f_in.close()
21.    f_out.close()
Dada a natureza do enunciado resolvemos natural tratar o problema linha a linha. Cada linha é partida e os seus números ordenados. Calculamos de seguida a média retirando o primeiro (o mais pequeno) e o último (o maior).

1 comentário:

  1. Ola, gostaria de saber sobre esse problema.

    Construa uma função que receba um ficheiro de texto como parâmetro e
    devolva um dicionário com cada uma das palavras do texto associada à lista de
    linhas em que ocorre no texto. Implemente instruções que testem a função.

    ResponderEliminar