Como criar uma "IA de tráfego"?

21

Um projeto em que estou trabalhando agora apresenta muito "tráfego" no sentido de carros se movendo pelas estradas, aeronaves se movendo em torno de um avental etc.

A partir de agora, os caminhos disponíveis são pré-calculados; portanto, os nós são gerados automaticamente para cruzamentos que são interconectados por arestas. Quando um personagem / agente aparece no mundo, ele inicia em algum nó e encontra o caminho para um nó de destino por meio de um algoritmo simplesmente A *. O agente segue o caminho e, finalmente, chega ao seu destino. Não há problema até agora.

Agora, preciso permitir que os agentes evitem colisões e lidem com situações complexas de tráfego. Como sou novo no campo da IA, procurei vários artigos / artigos sobre comportamento de direção, mas achei que eram de nível muito baixo. Meu problema consiste menos em evitar colisões reais (o que é bastante simples nesse caso, porque os agentes seguem caminhos estritamente definidos), mas em situações como um agente saindo de um beco sem saída, enquanto outro quer entrar exatamente no mesmo. Ou dois agentes se encontrando em um gargalo que permite apenas que um agente passe de cada vez, mas ambos precisam passar por ele (de acordo com a rota ideal encontrada anteriormente) e precisam encontrar uma maneira de deixar o outro passar primeiro. Então, basicamente, o principal aspecto do problema seria prever o movimento do tráfego para evitar bloqueios.

Difícil de descrever, mas acho que você entende o que quero dizer. Você tem alguma recomendação para mim sobre onde começar a procurar? Alguma documentação, projetos de amostra ou coisas semelhantes que possam me ajudar?

Eu aprecio sua ajuda!

Lunikon
fonte
A difusão colaborativa pode ajudá-lo com alguma coisa. É uma maneira simples de resolver o caminho pesquisando vários agentes ao mesmo tempo + agentes evitando a si mesmos. Por favor, compartilhe sua experiência com ela em algum lugar, obrigado. ;)
user712092 11/11

Respostas:

12

Há tantas maneiras de resolver esse problema que eu lutaria para dar uma resposta decente e abrangente aqui. Mas aqui estão alguns pontos de design de alto nível.

  • Você está construindo uma simulação de agente aqui. A busca de caminhos é simplesmente uma entrada no sistema - o agente tem um objetivo, e a busca de caminhos é apenas uma maneira de atingir esse objetivo. Na verdade, pensando nisso em termos reais, o agente tem dois objetivos: o principal objetivo de um motorista é "não bater", depois disso é "chegar onde eu quero ir".
  • Seus sistemas devem se basear em paralelos no mundo real. A razão pela qual a maioria das estradas tem duas ou mais faixas é porque é muito mais fácil organizar o tráfego com esse sistema, ninguém precisa pensar muito. Em um cenário de pista única, os motoristas precisam resolver vários problemas:

    detecção - reconhecendo que você e o carro que se aproxima batem, a menos que se evitem

    reação - desacelerando e entrando em uma fase de negociação.

    negociação - um dos motoristas tem que assumir a liderança, o outro tem que ceder. As regras para decidir isso são vagas, mas basicamente você quer algo em que um motorista arbitrariamente (ou com base em uma heurística sobre quantos carros estão vindo na outra direção) decide ter prioridade. Por exemplo, A tem prioridade no tempo 1, B vê A ter prioridade e produz (saindo do caminho e parando). Se A e B tentarem ter prioridade, ambos deverão parar, aguardar um período aleatório de tempo (ou sinalizar um ao outro) e tentar novamente. Eventualmente, um cederá ao outro.

    A vantagem dessa implementação é que ela evita a necessidade de manter filas artificiais ou outras construções falsas. A negociação é feita em termos de percepções do mundo real - uma vez que ambas as partes estão na fase de negociação, qualquer avanço significativo é facilmente detectado como uma tentativa de ter prioridade. Ele também deve reagir adequadamente ao usuário, que provavelmente não seguirá as boas regras de direção.

  • Suponha o pior. Mesmo em um sistema perfeito, situações estranhas podem surgir e seus atores devem agir com sensatez. Isso é ainda mais provável se o jogador puder interferir (bloquear áreas artificialmente, etc.) Freqüentemente, parar completamente é a única resposta sensata (bloqueio!) Girar no local ou, obviamente, estar em um estado quebrado é uma falha da IA. Parar completamente é pelo menos plausível em termos do mundo real.

    Quanto mais você modelar a IA do seu ator na lógica simples do mundo real, mais fácil será criar uma IA convincente. Pessoas reais não param ou oscilam para frente e para trás se não conseguem alcançar seu objetivo. Se o único caminho para o destino da IA ​​estiver bloqueado, eles devem reconhecer isso e escolher uma resposta (pare completamente, desista e volte para casa, desista e dirija para outro lugar).

  • Comportamentos de camada para obter o que deseja. Lembre-se, o primeiro objetivo não é falhar. Portanto, a lógica da prevenção (direção) deve sempre dominar as ações do motorista. Coloque em cima disso a lógica direcional que vem da descoberta do caminho ('eu quero virar à direita no próximo cruzamento'). Camada sobre essa ocasional reavaliação de caminhos, com lógica de nível superior ('prefere avançar, mas se eu não puder progredir, permita um novo caminho que envolva uma inversão de marcha').

  • A descoberta de caminhos vem da memória, mas a consciência situacional é baseada na percepção. Não tente fazer seus agentes perfeitos. Eles sabem o caminho de casa para o escritório, para saber quais são as voltas a serem feitas. Mas eles não sabem que a rua a 3 km está bloqueada. Não tente fazer com que seus agentes planejem um caminho perfeito, porque não há nenhum - mesmo que comece perfeito, outros fatores podem bloquear seu caminho. Os agentes só precisam planejar algumas ruas à frente para onde estão indo.

  • Qualidade da informação. Seus comportamentos devem ser simples, mas para conseguir isso, você precisa de uma boa funcionalidade de consulta. Você precisa fazer perguntas ao seu ambiente como "esse carro está ocupando minha pista?", "Quantos carros estão chegando?", "Existem carros atrás de mim", "posso fazer uma inversão de marcha" .

MrCranky
fonte
Obrigado pela sua resposta elaborada. Seu conselho deve ser realmente útil quando eu chegar ao tráfego rodoviário regular. Mas eu provavelmente não notei dois aspectos importantes no meu post inicial: 1. O jogador não participa do tráfego sozinho. É mais como um sim de negócios e ele constrói a rede. 2. Os caminhos unidirecionais ocorrem especialmente nos aeroportos, mas nos aeroportos os agentes não estão "sozinhos", mas têm uma torre dizendo a eles para onde ir. A torre precisa identificar as situações complicadas, mas também possui conhecimento total. Então, suponho que essa seja uma camada acima das situações / comportamentos que você descreveu.
Lunikon
5

Tendo visto algumas falhas horríveis nos jogos lançados, tenho algumas sugestões:

1) A menos que haja uma boa razão, faça duas faixas e, para fins de IA, faça com que elas tenham prioridade para uma direção normal do fluxo - permita viagens de duas a duas, mas se algo estiver vindo para o outro lado, o cara do lado errado da estrada sempre cede a ele.

2) Algum tipo de lógica para resolver um engarrafamento, se ocorrer. Eu assisti situações em que o manuseio do engarrafamento se aplicava apenas aos veículos que estavam tentando se encontrar, mas que falharam totalmente quando confrontados com um padrão -> -> <- <-. Lembro-me de um mapa que era propenso a isso - era um ponto de estrangulamento destinado a tornar a base da IA ​​mais difícil de atacar, mas mais cedo ou mais tarde dois coletores de recursos chegariam enquanto um grupo de ataque estava saindo e foi isso. As unidades em contato giravam ao redor, tentando encontrar uma rota, mas não tinham movimentos legais. Ele não voltou atrás e descobriu que alguma outra unidade tinha que se mover primeiro e, portanto, a IA não tomou ações úteis até que o bloqueio fosse removido. (Você pode assistir as unidades em contato girando e nada mais faz nada.)

Acredito que isso poderia ser resolvido, fazendo uma unidade presa dizer às unidades vizinhas que se afastassem - isso se propagaria até chegar a uma unidade livre que pudesse recuar. Isso teria que envolver algum tipo de lógica para mantê-los afastados até que o problema fosse resolvido.

Observe que simplesmente procurar um caminho alternativo geralmente é uma resposta ruim. Eu assisti a uma situação de livelock desse tipo - a unidade A observa que B está bloqueando a estrada à frente e, portanto, ela se vira para usar uma rota diferente. Isso agora bloqueia a estrada para B que se vira - agora a estrada está desbloqueada, então as duas se viram novamente. Cada turno alternam entre avançar e recuar.

O mesmo jogo que eu já vi uma versão diferente, também devido ao nevoeiro da guerra. Havia uma unidade inimiga no ponto de estrangulamento. Ao mover-se automaticamente, a busca de caminhos não lutaria, a menos que seja realmente direcionada à unidade inimiga. Ele avançaria e veria a estrada bloqueada. Depois voltou, não pôde mais ver o bloqueador e seguiu em frente novamente. Repita até o humano perceber que não estava chegando aonde deveria ir.

Loren Pechtel
fonte
2
Boa resposta - eu gosto da noção de transmitir mensagens "presas" para que qualquer pessoa que possa sair o faça.
21311 MrCranky
4

Não tenho muita experiência com simulações de tráfego, mas algumas coisas vêm à mente.

Em primeiro lugar, para evitar gargalos, em primeiro lugar, eu teria duas faixas que permitem que os veículos viajem em direções opostas. na mesma "estrada".

Em segundo lugar, para colisões que possam ocorrer, você deve ter um comportamento de direção de prevenção de colisões para evitar uma acumulação maciça. Os comportamentos de direção podem ser de baixo nível, mas são muito úteis na criação de comportamentos emergentes com aparência realista.

Se você não quiser ter mais de uma faixa, precisará armazenar mais informações no gráfico. Por exemplo, se o agente A estiver em uma estrada (representada como uma aresta do gráfico) e o agente B estiver na mesma estrada, movendo-se na direção oposta a A, eles serão colidir / impasse / whatever que você codificado para lidar com esse comportamento.

No entanto, se o agente A estiver em uma estrada, ele poderá solicitar a propriedade dessa estrada. Possuir a estrada significaria que nenhum outro agente pode viajar ao longo dessa borda (você pode fazer isso simplesmente alterando o custo da borda para um número enorme para garantir que A * não escolha a estrada ao calcular um caminho). Então, quando o agente A está livre dessa estrada, ele renuncia à propriedade.

Honestamente, é uma solução hacky da qual não gosto particularmente e a maioria das simulações de tráfego (se não todas?) Que vi usar uma abordagem de várias faixas.

Ray Dey
fonte
Sim, duas faixas devem ser usadas (porque simplesmente existem duas faixas), mas isso não resolve nenhum problema que trate de ceder (que são a maioria dos problemas descritos pelo autor da pergunta)
Bart van Heukelom
4

Você disse que procurou vários artigos sobre comportamento de direção, embora apenas no caso, você procurou no seguinte?

http://www.red3d.com/cwr/steer/

Caso contrário, poderá fornecer algumas respostas, pois abrange alguns dos problemas que você nomeou, por exemplo, o problema de gargalo (enfileiramento).

Tyrfing
fonte
0

Eu acho que o que você precisa fazer é implementar um algoritmo de localização de caminho.

Divida o mapa em pedaços tão pequenos quanto possível (digamos quadrados), mas apenas para lugares válidos para o tráfego viajar. Você determinaria onde o veículo está e para onde está indo e encontraria um caminho, mais curto ou mais direto, talvez. O caminho será uma matriz de quadrados, a cada passo do caminho para a destruição. O que você deseja então é calcular não apenas a posição atual de todos os veículos, mas também as posições futuras dos veículos para algumas etapas no futuro. Se dois veículos estiverem no mesmo quadrado no futuro, você precisará alterar a velocidade de um ou de ambos.

A * (Uma estrela) é um algoritmo de localização de caminho muito simples que você provavelmente pode facilmente traduzir o código psuedo na wikipedia para o seu idioma preferido e funcionará: http://en.wikipedia.org/wiki/A*_search_algorithm

justin.m.chase
fonte
4
Como mencionei no meu post inicial, já implementei um algoritmo A * e também tenho estruturas de dados correspondentes. Além disso, apenas reduzir a velocidade de qualquer um dos agentes parece um pouco "fácil" para mim.
Lunikon
Este não é um problema de localização de caminho, é um problema de simulação de agente. A descoberta de caminhos é apenas o nível mais baixo de inteligência que os atores precisam aplicar.
21311 MrCranky
Muito fácil? haha Bem, é isso que faço quando estou dirigindo! Se eu posso prever uma colisão com meu caminho atual, mudo minha velocidade.
usar o seguinte código
E semáforos? E o que fazer quando seu caminho é bloqueado por outro veículo? O que fazer quando o caminho diz para a frente, mas sua velocidade é zero para evitar uma colisão. Uma colisão com outro carro, cujo caminho diz seguir em frente (através de você) e a velocidade deles também é zero?
21811 MrCranky
Em um cenário de pista única, se você usar a velocidade de outros carros para calcular seus destinos futuros quando o primeiro carro detectar a colisão e parar o outro carro, também não precisará parar, pois a velocidade do primeiro carro é agora 0. Isso pressupõe que você será capaz de olhar com bastante antecedência a tempo de ver colisões com carros em longas estradas de pista única. Um amigo meu sugere que você adicione um nó STOP ao seu algoritmo A * também. Com isso da perspectiva de qualquer carro, você consideraria outros carros um obstáculo. Parar pode desbloquear o caminho se for feito o suficiente.
usar o seguinte código
0

Quando eu implementei o Inemy Nations, meu retorno final foi que, se um veículo permaneceu preso por mais de 2 segundos, eu pulei para frente em seu caminho. Então, quando eles ficaram presos, uma unidade basicamente transportada. Ninguém nunca reclamou, então eu acho que nas poucas vezes que isso aconteceu, ninguém estava assistindo e não viu.

David Thielen
fonte