Atualizando registro quando referenciado por várias estruturas de dados

Suponha que eu tenha um registro, por exemploPersone quero ser capaz de ver essa pessoa através de várias estruturas de dados. Talvez haja um índice pelo nome, outro índice pelo código postal da pessoa e outro índice pela latitude e longitude atuais da pessoa. E talvez muitas outras estruturas de dados. Todos os que existem porque eu preciso procurar com eficiência uma pessoa ou pessoas com critérios diferentes.

Se eu apenas precisarler atributos de uma pessoa,Isso não é problema. Mas agora suponha que eu precise procurar uma pessoa usando uma dessas estruturas de dados e depoisatualizar os dados da pessoa.

Em uma linguagem OOP, cada estrutura de dados apontaria para a mesma pessoa na memória. Então, quando você atualiza um, você está implicitamente atualizando os referentes das outras estruturas de dados também. Isso é basicamente a definição de efeitos colaterais e impureza. Eu sei que é totalmente contra o paradigma Haskell, e eu não estou esperando que Haskell trabalhe dessa maneira.

Então, qual é a maneira Haskell-ish para fazer isso? Para ser claro, o problema é este: eu procuro uma pessoa por uma estrutura de dados, e eu passo essa pessoa (e talvez alguns outros dados arbitrários) em uma função do tipoArbitraryData -> Person -> Person. Como faço para propagar essa alteração em todas as várias estruturas de pesquisa?

Como recém-chegado a Haskell, meu primeiro instinto é reconstruir toda estrutura de pesquisa com a pessoa recém-atualizada, toda vez que eu atualizo uma pessoa. Mas parece muita cerimônia, com muitas oportunidades para eu estragar de uma forma que o GHC não consegue detectar, e não é nada elegante. Haskell é conhecida por sua elegância, e não posso imaginar que não tenha uma solução elegante para um problema tão comum e básico. Então eu acho que estou perdendo alguma coisa.

Para referência, esta questão se expande em algumas das questões que eu estava discutindo nas seguintes questões:

Várias estruturas de pesquisa para os mesmos dados: duplicação de memória?

Identidade de objetos de simulação em Haskell

Editar

Uma solução que me passou pela cabeça: não mantenha uma cópia de cada estrutura de pesquisa no seu estado principal. Apenas mantenha uma única lista de todas as pessoas existentes, e essa é a única coisa que precisamos atualizar quando atualizamos uma pessoa. Toda vez que você precisar procurar por, digamos, código postal, passe a lista de todas as pessoas para uma função que gere a eficiente estrutura de dados por código postal. Em seguida, execute a pesquisa no resultado.

Não sei se isso seria eficiente. Se isso resultar na CPU recomputando a estrutura de pesquisa em cada uso, isso é inaceitável. Mas eu sei que Haskell às vezes pode evitar reavaliar expressões idênticas. Infelizmente, ainda não descobriquando este é o caso. Então não sei se essa abordagem é viável.

Então, em outras palavras: posso escrever minhas funçõesAté parece eles estão computando a pesquisa toda vez que, na verdade, o GHC irá otimizá-lo para casos em que os dados subjacentes não mudaram? Porque isso seria ummuito solução elegante para o problema que eu identifiquei acima.

questionAnswers(7)

yourAnswerToTheQuestion