existência: para todo o n existe pelo menos uma sequência de Langford?
construção: se existe L(n), como obtê-la?
enumeração: quantas sequências de ordem n existem?
geração: as sequências de ordem n podem ser geradas sistematicamente?
optimização: quais as soluções que maximizam (ou minimizam) f(L(n)) para uma dada função objectivo f?
O problema de Langford consiste em encontrar uma sequência de Langford para um dado n. Trata-se na realidade de um caso especial do problema combinatório mais geral conhecido por problema da cobertura exacta. Mas quem é que se pode interessar por isto? Bem, para além do prazer de brincar com a matemática, existem exemplos de aplicação concreta: resolver um problema do Sodoku é resolver um problema de cobertura exacta. O problema da cobertura exacta é um problema combinatório de elevada complexidade (*), sendo que para valores elevados de n não existe um computador suficientemente rápido, nem hoje nem amanhã, que o resolva em tempo útil. Mas nós não vamos discutir estas questões. Vamos começar por criar um programa simples que nos diz, para todo o n, se uma dada sequência é de Langford ou não. Vamos admitir que para um dado n a sequência tem comprimento de 2*n e cada inteiro entre 1 e n ocorre exactamente duas vezes. Vamos a isso.
Como resolver o problema? Vamos pensar num caso mais simples: como saber se um dado k tem k inteiros entre as suas duas ocorrências? Bem, basta encontrar as posições entre as duas ocorrências e contar as posições entre ambas. E para todos? Também não é difícil: repetir para todos inteiros no intervalo [1,n]. Asim vamos ter um ciclo repetido n vezes que faz a verificação da condição. Claro que se existir um número que não verifique a condição podemos logo abandonar o programa pois já sabemos a resposta.
01.
def
testa_langford(seq):
02.
"""Verifica se seq é uma sequência de Langford."""
03.
ordem
=
len(seq)
/
/
2
04.
for
k
in
range(
1
,ordem
+
1
):
05.
indice_1
=
seq.index(k)
06.
indice_2
=
seq.index(k,indice_1
+
1
,len(seq))
07.
if
(indice_2
-
indice_1
-
1
) !
=
k:
08.
return
False
09.
return
True
1.
def
candidata(seq):
2.
“””Pode ser sequência de Langford?”””
3.
n
=
len(seq)
/
/
2
4.
for
k
in
range(
1
,n
+
1
):
5.
if
seq.count(k) !
=
2
:
6.
return
False
7.
return
True
01.
def
candidata(seq):
02.
“””Pode ser sequência de Langford?”””
03.
if
len(seq)
%
2
!
=
0
:
04.
return
False
05.
06.
n
=
len(seq)
/
/
2
07.
for
k
in
range(
1
,n
+
1
):
08.
if
seq.count(k) !
=
2
:
09.
return
False
10.
return
True
01.
def
qualidade(seq):
02.
"""Conta o número de números que satisfaz a condição e Langford."""
03.
ordem
=
len(seq)
/
/
2
04.
conta
=
0
05.
for
i
in
range(
1
,ordem
+
1
):
06.
indice_1
=
seq.index(i)
07.
indice_2
=
seq.index(i,indice_1
+
1
,len(seq))
08.
if
(indice_2
-
indice_1
-
1
) !
=
i:
09.
conta
+
=
1
10.
return
conta
(*) Tecnicamente diz-se que é um problema NP-Completo.
Sem comentários:
Enviar um comentário