Modelando emaranhamento quântico em C #

À medida que o tópico do entrelaçamento quântico aparece cada vez mais, eu queria ir um pouco mais fundo. A julgar pelos comentários nos artigos sobre entrelaçamento quântico, essas informações não serão úteis apenas para mim. Bem, levando em consideração o fato de que, para a maioria de nós, o código do programa é muito mais conveniente do que qualquer alegoria, foi decidido apresentar meu entendimento na forma de código.

Este artigo estende o artigo de outro autor , "Quantum Entanglement for Dummies" (eu recomendo a leitura, isso me ajudou muito). Em seu artigo, indomit deu um exemplo de um programa que demonstra claramente o problema da teoria dos parâmetros ocultos, mas não poderia dar um exemplo de um código para partículas em superposição. Neste artigo, tentaremos simular 2 casos:

  1. Como as partículas entrelaçadas se comportariam no determinismo, quando o estado das partículas é estabelecido antes da medição, simplesmente não podemos medi-lo sem introduzir distorções (a própria teoria dos parâmetros ocultos). Obtemos os números e vemos a discrepância com a prática.
  2. Escreveremos um modelo de partículas emaranhadas em superposição (o estado das partículas não é definido antes da medição). Vamos tentar assumir como a partícula é programada dentro, ou seja, ajustaremos seu código aos dados obtidos experimentalmente.

O artigo baseia-se na explicação popular do fenômeno do entrelaçamento quântico de Mermin:

O Paradoxo de Mermin Explicado
Para o relato popular do paradoxo, D. Mermin propõe construir um dispositivo simples [23]. O dispositivo deve consistir de um emissor de partículas e dois detectores. Duas partículas idênticas são emitidas para cada uma delas. Depois de capturar uma partícula, o detector fornece uma resposta binária (0 ou 1), dependendo da partícula e do interruptor de ajuste de três posições. A detecção de um par de partículas deve fornecer as mesmas respostas:

  1. Sempre que os detectores são configurados da mesma maneira.
  2. Segundo as estatísticas, na metade dos casos, quando são configurados aleatoriamente.

A primeira propriedade requer que todos os detectores usem a mesma codificação, a posição do comutador é ∈ {1,2,3} ↦ resposta ∈ {0,1}, sem nenhum elemento aleatório. Ou seja, eles devem concordar antecipadamente qual das respostas, 0 ou 1, fornece à posição do comutador, escolhendo para cada partícula uma das oito funções possíveis, 000, 001, 010, 011, 100, 101, 110 e 111. A escolha de 000 ou 111 resultará em 100% de coincidência das leituras dos detectores, independentemente da posição do botão de controle. Se os detectores implementarem uma das seis funções restantes, um dos dígitos é pressionado por um interruptor sintonizado aleatoriamente em 2/3 dos casos, o outro com uma probabilidade de 1/3. A probabilidade de coincidência das duas respostas será (⅔) ² + (⅓) ² = 5/9. Portanto, não importa qual seja o algoritmo do autômato, a correlação inevitavelmente excede 50%, violando o segundo requisito.

Mas como essa máquina ainda pode ser construída (por exemplo, posicionando os polarizadores a 120 ° como no experimento de Bohm), não pode haver determinismo (parâmetros), mesmo de forma oculta. Em vez disso, as correlações de resposta são mantidas pela transmissão de informações de uma partícula "medida" para outra mais rapidamente que a segunda medição.

Retirado daqui .

Infelizmente, eu não pratico física nem profissionalmente nem no nível amador, não finjo ser impecável. O objetivo principal do artigo é demonstrar como tornar um modelo compreensível para aqueles familiarizados com a programação. Se alguém trabalha profissionalmente nesse campo, em vez de censurar, tente escrever modelos de interação mais precisos com base no meu artigo.

[Update] Explicação da descrição do Mermin


Embora vários meses se passaram desde a redação do artigo e ninguém retorne a ele, decidi fazer um esclarecimento para acalmar minha consciência.

Fui um pouco mais fundo e cheguei à conclusão de que a descrição de acordo com Mermin é bastante simplificada e as tentativas de vinculá-la a experimentos físicos reais não têm sentido .

Inicialmente, tentei vincular o artigo a um experimento real com polarização circular e cometi um erro nisso. O ARad tentou desenvolver uma ligação a experimentos físicos reais, escreveu sobre os erros cometidos e até propôs sua própria versão do código (que também não corresponde a nenhum experimento físico).

Para que o artigo fizesse algum sentido, foi decidido remover todos os links imaginários de experimentos físicos reais e simplesmente explicar a descrição de Mermin no código e torná-lo mais visual. Experimentos reais são mais complicados e, para simulá-los, você precisa gastar muito mais tempo.

Na primeira versão do artigo, aceitamos que no primeiro experimento (a posição dos sensores coincide) as partículas dão um resultado espelhado, mas na descrição original de acordo com Mermin, o resultado da medição com a mesma posição dos sensores sempre coincide. Isso está consertado .

Além disso, acrescentarei uma "explicação para uma explicação" deste próprio Mermin, uma vez que não está escrito sem ambiguidade:

Ou seja, eles devem concordar antecipadamente qual das respostas, 0 ou 1, atribui à posição do comutador, escolhendo para cada partícula uma das oito funções possíveis, 000, 001, 010, 011, 100, 101, 110 e 111.

A frase "oito funções possíveis" é ambígua. Oito variantes possíveis do impacto potencial de partículas no sensor são discutidas. O sensor possui três posições (veja a descrição completa acima). Se acreditarmos que o estado das duas partículas coincide e é definido com antecedência, podemos determinar com antecedência qual resposta (0 ou 1) receberemos potencialmente para cada uma das três posições do comutador (embora possamos "medir" apenas uma das três opções).

Selecionar 000 ou 111 resultará em 100% de correspondência das leituras do detector, independentemente da posição do botão de ajuste.

Se as partículas puderem assumir um valor no qual possamos receber potencialmente uma resposta "1" para qualquer posição do comutador (assim como 0 para qualquer posição do comutador), o segundo experimento nesses casos fornecerá 100% de coincidência. Para se aproximar de 50%, essas opções podem ser excluídas.

Se os detectores implementarem uma das seis funções restantes, um dos dígitos é pressionado por um interruptor sintonizado aleatoriamente em 2/3 dos casos, o outro com uma probabilidade de 1/3.

Isso significa que em cada um dos 6 triplos (001, 010, 011, 100, 101, 110) - apenas dois dos três dígitos correspondem (na primeira versão, dois dos três são "0" e um dos três é "1" )

Para avaliar a probabilidade, compilamos uma tabela para o primeiro caso 001 :

Posição do sensor 1Posição do sensor 2As medidas correspondem
11+
12+
13-
21+
22+
23-
31-
32-
33+

Pode-se observar que em cinco casos de nove medições coincidem. A mesma probabilidade será para cada uma dessas seis opções (afinal, em cada uma delas os dois números são iguais).

Medições


Em cada um dos modelos (determinísticos e superposicionais), realizaremos dois experimentos com partículas emaranhadas correspondentes às primeira e segunda condições de acordo com Mermin:

  1. Primeiro, coloque os dois sensores na mesma posição. Nesse caso, obteremos resultados 100% idênticos (se o primeiro fóton passar pelo polarizador, o fóton associado também passará pelo polarizador no mesmo ângulo).
  2. Em seguida, definiremos a posição dos sensores aleatoriamente.

Aqui está o código para o primeiro experimento:

var totalAttempts = 10000; //   var coincidenceCount = 0; //    for (int attemptNumber = 1; attemptNumber <= totalAttempts; attemptNumber++) { var entanglementParticles = new EntanglementParticles(); //     var position = GetRandomInteger(1, 3); //        //            int firstSensorPosition = position; int secondSensorPosition = position; bool firstValue = entanglementParticles.First.GetValue(firstSensorPosition); //         bool secondValue = entanglementParticles.Second.GetValue(secondSensorPosition); //         if (firstValue == secondValue) //     coincidenceCount ++; } Console.WriteLine(" №1: {0}%  ", (decimal)coincidenceCount / totalAttempts * 100); //   

Aqui está o código para o segundo experimento:

 var totalAttempts = 10000; //   var coincidenceCount = 0; //    for (int attemptNumber = 1; attemptNumber <= totalAttempts; attemptNumber++) { var entanglementParticles = new EntanglementParticles(); //     int firstSensorPosition = GetRandomInteger(1, 3); //      1 int secondSensorPosition = GetRandomInteger(1, 3); //      2 bool firstValue = entanglementParticles.First.GetValue(firstSensorPosition); //         bool secondValue = entanglementParticles.Second.GetValue(secondSensorPosition); //         if (firstValue == secondValue) //     coincidenceCount ++; } Console.WriteLine(" №2: {0}%  ", (decimal)coincidenceCount / totalAttempts * 100); 

Os mesmos testes serão para todos os modelos de partículas, apenas o código de partículas será diferente para os modelos determinístico e de superposição (mais sobre isso abaixo).

Modelo determinístico


Atenção! Veja ATUALIZAÇÃO no final do artigo!

Para quem deseja executar imediatamente o código, isso pode ser feito no navegador: dotnetfiddle.net/N5Xg18

Então, de acordo com a explicação de Mermin, temos uma partícula quântica com 3 parâmetros:

 //   ( , ) public class Particle { private bool _measured = false; public bool A { get; private set; } //       1 public bool B { get; private set; } //       2 public bool C { get; private set; } //       3 public Particle(bool a, bool b, bool c) { A = a; B = b; C = c; } //         ( 3 ). public bool GetValue(int sensorPosition) { if (_measured) throw new InvalidOperationException("    !"); _measured = true; switch (sensorPosition) { case 1: return A; case 2: return B; case 3: return C; default: throw new ArgumentOutOfRangeException(); } } } 

Como o modelo é determinístico, todos os parâmetros da partícula são inicializados no momento de sua criação, ou seja, diretamente no construtor. A única condição é que a medição seja permitida apenas uma vez!

Próximo. Um par de partículas emaranhadas:

 //    public class EntanglementParticles { public Particle First { get; private set; } //   public Particle Second { get; private set; } //   //     (   ,         ) public EntanglementParticles() { //         bool a; bool b; bool c; do { a = GetRandomBoolean(); //     1 b = GetRandomBoolean(); //     2 c = GetRandomBoolean(); ; //     3 } while (a == b && b == c); //   000  111 (    ,       ) First = new Particle(a, b, c); Second = new Particle(a, b, c); //       } } 


Pode-se observar que os valores de cada uma das partículas são definidos no momento da criação de um par de partículas emaranhadas, e os parâmetros da segunda partícula correspondem aos parâmetros da primeira (sem isso, não podemos passar no primeiro teste). Utilizamos números aleatórios, mas, de acordo com o modelo, os parâmetros dependem de fatores no momento do emaranhado (como resultado da roleta, depende de vários fatores no momento de desenroscar).

Código de exemplo completo:

Código C # do modelo determinístico (fixo)
 using System; public class Program { private static readonly Random Random = new Random(); //   public class Particle { private bool _measured = false; public bool A { get; private set; } //       1 public bool B { get; private set; } //       2 public bool C { get; private set; } //       3 public Particle(bool a, bool b, bool c) { A = a; B = b; C = c; } //         ( 3 ). public bool GetValue(int sensorPosition) { if (_measured) throw new InvalidOperationException("    !"); _measured = true; switch (sensorPosition) { case 1: return A; case 2: return B; case 3: return C; default: throw new ArgumentOutOfRangeException(); } } } //    public class EntanglementParticles { public Particle First { get; private set; } //   public Particle Second { get; private set; } //   //     (   ,         ) public EntanglementParticles() { //         bool a; bool b; bool c; do { a = GetRandomBoolean(); //     1 b = GetRandomBoolean(); //     2 c = GetRandomBoolean();; //     3 } while (a == b && b == c); //   000  111 (   ,       ) First = new Particle(a, b, c); Second = new Particle(a, b, c); //       } } public static void Main(string[] args) { Experiment1(); Experiment2(); } private static void Experiment1() { var totalAttempts = 10000; //   var coincidenceCount = 0; //    for (int attemptNumber = 1; attemptNumber <= totalAttempts; attemptNumber++) { var entanglementParticles = new EntanglementParticles(); //     var position = GetRandomInteger(1, 3); //        //            int firstSensorPosition = position; int secondSensorPosition = position; bool firstValue = entanglementParticles.First.GetValue(firstSensorPosition); //         bool secondValue = entanglementParticles.Second.GetValue(secondSensorPosition); //         if (firstValue == secondValue) //     coincidenceCount ++; } Console.WriteLine(" №1: {0}%  ", (decimal)coincidenceCount / totalAttempts * 100); //   } private static void Experiment2() { var totalAttempts = 10000; //   var coincidenceCount = 0; //    for (int attemptNumber = 1; attemptNumber <= totalAttempts; attemptNumber++) { var entanglementParticles = new EntanglementParticles(); //     int firstSensorPosition = GetRandomInteger(1, 3); //      1 int secondSensorPosition = GetRandomInteger(1, 3); //      2 bool firstValue = entanglementParticles.First.GetValue(firstSensorPosition); //         bool secondValue = entanglementParticles.Second.GetValue(secondSensorPosition); //         if (firstValue == secondValue) //     coincidenceCount ++; } Console.WriteLine(" №2: {0}%  ", (decimal)coincidenceCount / totalAttempts * 100); } private static bool GetRandomBoolean() { return GetRandomInteger(0, 1) == 1; } private static int GetRandomInteger(int from, int to) { return Random.Next(from, to + 1); //          } } 


Você pode iniciá-lo no navegador (mais uma vez no link: dotnetfiddle.net/N5Xg18 ).

Após o lançamento, estes são os resultados:

Experiência nº 1: 100% dos valores coincidiram
Experiência nº 2: 55,6700% dos valores correspondentes

O primeiro teste aprovado, corresponde ao que está acontecendo na realidade. Mas o segundo - não corresponde, pois devem receber 50%!

Como resultado, os físicos foram forçados a chegar à conclusão de que a teoria dos parâmetros ocultos é errônea. E com isso, o princípio da localidade é refutado e o princípio da causalidade foi até abalado.

Modelo de superposição


Imediatamente um link para um código de exemplo, para quem gosta de detalhes (pode ser iniciado em um navegador): dotnetfiddle.net/Mb7JqU

Para explicar os resultados obtidos durante os experimentos, foi necessário o uso de modelos mais complexos. Nos modelos modernos, o estado dos parâmetros das partículas não é definido antes da medição e as próprias partículas emaranhadas têm a capacidade de afetar instantaneamente (além da velocidade da luz) o estado uma da outra. Aqui está a aparência do nosso modelo de partículas agora:

 //   public class Particle { private Particle _superluminalChannel; //         . private int? _measuredPosition; public bool? A { get; private set; } //       1 public bool? B { get; private set; } //       2 public bool? C { get; private set; } //       3 internal void CreateSuperluminalChannelWith(Particle particle) { _superluminalChannel = particle; } //         ( 3 ). public bool GetValue(int sensorPosition) { if (null != _measuredPosition) throw new InvalidOperationException("    !"); _measuredPosition = sensorPosition; if (null != _superluminalChannel._measuredPosition) //        { var measuredValue = _superluminalChannel.GetNakedValue(); //         (    ),   ,     . if (sensorPosition == _superluminalChannel._measuredPosition) return measuredValue; if (GetRandomInteger(1, 4) == 1) return measuredValue; return !measuredValue; } //  .        ,       -  . //   ! var value = GetRandomBoolean(); SetValue(sensorPosition, value); return value; } private bool GetNakedValue() //           ,    . { if (null == _measuredPosition) throw new InvalidOperationException(); switch (_measuredPosition.Value) { case 1: return A.Value; case 2: return B.Value; case 3: return C.Value; default: throw new InvalidOperationException(); } } private void SetValue(int position, bool value) { switch (position) { case 1: A = value; break; case 2: B = value; break; case 3: C = value; break; default: throw new ArgumentOutOfRangeException(); } } } 

Primeiro, os parâmetros são Anuláveis ​​(eles podem não importar) e não os definimos no construtor. Em segundo lugar, o método CreateSuperluminalChannelWith para definir o canal superluz entre partículas, ou seja, Agora, uma partícula pode obter o estado de outra instantaneamente, independentemente da distância. Bem, e mais importante, agora o estado de uma partícula é estabelecido apenas no momento da medição (chamando o método GetValue) e depende se outra partícula relacionada a ela foi medida.

O interior do método GetValue é pura especulação. Ninguém sabe como a partícula é organizada no interior, mas sabemos que funciona assim: 100% de incompatibilidade ao medir o mesmo parâmetro e 50% de incompatibilidade ao medir parâmetros em uma ordem aleatória.

Na minha versão do código, uma partícula através de um canal superluminal verifica se a medição é confundida com ela e age assim:

  1. Se o parâmetro medido de outra partícula for o mesmo que estamos tentando medir, ele fornecerá o mesmo valor.
  2. Se o parâmetro for diferente, em 1/4 dos casos, obtém o mesmo valor, e em 3/4 dos casos, fornece o valor oposto (já que obtemos 50/50).

Se a medição não foi realizada, a partícula usa a aleatoriedade verdadeira para definir seu valor, ou seja, uma relação causal é violada (o valor não existia antes da medição e a própria medição não determinava seu valor).

A propósito! Você pode reescrever essa função de outra maneira, mas para que os resultados do teste sejam os mesmos. Mesmo assim, ninguém sabe como a partícula elementar é organizada e como 50% é alcançado no segundo teste.

Um par de partículas emaranhadas ficou mais fácil, pois no momento do emaranhamento nenhum valor é definido (os valores ainda não foram determinados):

 //    public class EntanglementParticles { public Particle First { get; private set; } //   public Particle Second { get; private set; } //   //     (  ,   ) public EntanglementParticles() { First = new Particle(); //   ,    Second = new Particle(); //   ,    //         First.CreateSuperluminalChannelWith(Second); Second.CreateSuperluminalChannelWith(First); } } 

Código de exemplo completo:

Modelo de superposição em C #
 using System; public class Program { private static readonly Random Random = new Random(); //   public class Particle { private Particle _superluminalChannel; //         . private int? _measuredPosition; public bool? A { get; private set; } //       1 public bool? B { get; private set; } //       2 public bool? C { get; private set; } //       3 internal void CreateSuperluminalChannelWith(Particle particle) { _superluminalChannel = particle; } //         ( 3 ). public bool GetValue(int sensorPosition) { if (null != _measuredPosition) throw new InvalidOperationException("    !"); _measuredPosition = sensorPosition; if (null != _superluminalChannel._measuredPosition) //        { var measuredValue = _superluminalChannel.GetNakedValue(); //         (    ),   ,     . if (sensorPosition == _superluminalChannel._measuredPosition) return measuredValue; if (GetRandomInteger(1, 4) == 1) return measuredValue; return !measuredValue; } //  .        ,       -  . //   ! var value = GetRandomBoolean(); SetValue(sensorPosition, value); return value; } private bool GetNakedValue() //           ,    . { if (null == _measuredPosition) throw new InvalidOperationException(); switch (_measuredPosition.Value) { case 1: return A.Value; case 2: return B.Value; case 3: return C.Value; default: throw new InvalidOperationException(); } } private void SetValue(int position, bool value) { switch (position) { case 1: A = value; break; case 2: B = value; break; case 3: C = value; break; default: throw new ArgumentOutOfRangeException(); } } } //    public class EntanglementParticles { public Particle First { get; private set; } //   public Particle Second { get; private set; } //   //     (  ,   ) public EntanglementParticles() { First = new Particle(); //   ,    Second = new Particle(); //   ,    //         First.CreateSuperluminalChannelWith(Second); Second.CreateSuperluminalChannelWith(First); } } public static void Main(string[] args) { Experiment1(); Experiment2(); } private static void Experiment1() { var totalAttempts = 10000; //   var coincidenceCount = 0; //    for (int attemptNumber = 1; attemptNumber <= totalAttempts; attemptNumber++) { var entanglementParticles = new EntanglementParticles(); //     var position = GetRandomInteger(1, 3); //        //            int firstSensorPosition = position; int secondSensorPosition = position; bool firstValue = entanglementParticles.First.GetValue(firstSensorPosition); //         bool secondValue = entanglementParticles.Second.GetValue(secondSensorPosition); //         if (firstValue == secondValue) //     coincidenceCount ++; } Console.WriteLine(" №1: {0}%  ", (decimal)coincidenceCount / totalAttempts * 100); //   } private static void Experiment2() { var totalAttempts = 10000; //   var coincidenceCount = 0; //    for (int attemptNumber = 1; attemptNumber <= totalAttempts; attemptNumber++) { var entanglementParticles = new EntanglementParticles(); //     int firstSensorPosition = GetRandomInteger(1, 3); //      1 int secondSensorPosition = GetRandomInteger(1, 3); //      2 bool firstValue = entanglementParticles.First.GetValue(firstSensorPosition); //         bool secondValue = entanglementParticles.Second.GetValue(secondSensorPosition); //         if (firstValue == secondValue) //     coincidenceCount ++; } Console.WriteLine(" №2: {0}%  ", (decimal)coincidenceCount / totalAttempts * 100); } private static bool GetRandomBoolean() { return GetRandomInteger(0, 1) == 1; } private static int GetRandomInteger(int from, int to) { return Random.Next(from, to + 1); //          } } 


Resultados:

Experiência nº 1: 100% dos valores coincidiram
Experiência nº 2: 49,7700% dos valores coincidiram

Executar no navegador: dotnetfiddle.net/Mb7JqU

Conclusões


Gostaria de mais interpretações disponíveis, como as expressas por Mermin. Com base nessa interpretação, consegui criar modelos visuais de teorias existentes e até apresentar um modelo alternativo, e esses modelos não são alegóricos - você pode executá-los e ver como eles funcionam.

Infelizmente, não tenho recursos de tempo para um conhecimento mais profundo da física quântica e espero que aqueles que conhecem possam seguir o meu exemplo e fornecer modelos de trabalho mais precisos.

ATUALIZAÇÃO
A explicação de Mermin não tem nada a ver com o design de detectores. Por minha própria iniciativa, adicionei uma explicação para A, B e C como uma projeção da rotação nos eixos X, Y e Z, respectivamente. Ou seja, eu queria adicionar uma ligação aos fenômenos físicos nos comentários ao código para que não ficasse tão seco. E eu estava enganado nisso ...

O artigo é corrigido e todas as tentativas vãs de vincular a explicação de Mermin a experimentos físicos reais são excluídas.

Source: https://habr.com/ru/post/pt420611/


All Articles