Algoritmos para plotagem de funções (adaptável?)

21

Estou procurando algoritmos para desenhar gráficos 2D padrão para funções que podem ou não ter singularidades. O objetivo é escrever um "Mini-CAS", para que eu não tenha conhecimento a priori dos tipos de funções que os usuários desejam representar graficamente.

Esse problema é muito antigo, então imagino que deve haver alguns algoritmos padrão na literatura. Pela primeira vez, não tive muito sucesso em encontrar referências via Google.

Eu encontrei um algoritmo interessante, este do "YACAS - Livro de algoritmos" chamado "Gráfico de funções adaptativas".

Então, resumindo:

  • Existem algoritmos padrão?
  • Existe um conjunto de testes para funções conhecidas de difícil plotagem?
  • Quais são os artigos interessantes para ler?
soegaard
fonte
2
Talvez a questão seja melhor entendida com "plotagem de funções" em vez de "desenho gráfico"? Eu interpretei mal o título no início (teoria dos grafos).
Astrojuanlu # 30/12
@ Juanlu001 Obrigado pela sugestão. Eu mudei o título.
Soegaard
Quando você diz 2D, você quer plotar uma função de uma variável como ou também está interessado em uma função de duas variáveis ​​( ) mostrada em 2D com, por exemplo, cores / tons diferentes representando valores diferentes? f ( x , y )f(x)f(x,y)
Szabolcs
Bem, eu quis dizer traçar uma função de uma variável. No entanto, eu também gostaria de ouvir sobre algoritmos para escolher quais pontos avaliar em uma configuração de duas variáveis ​​também. Eu não estou tão interessado em ouvir sobre cores e sombras.
Soegaard
Para funções 2D, veja minha pergunta e resposta aqui . O que fiz lá foi bastante limitado e não funcionará tão bem para funções arbitrárias. Além disso, existem algumas etapas essenciais que faltam na descrição sem as quais o método não converge adequadamente: eu precisava inserir um novo ponto de amostragem no meio de cada extremidade da malha que desapareceria na próxima retriangulação. (continuação)
Szabolcs

Respostas:

10

Eu implementei a rotina de amostragem adaptativa do Mathematica aqui no GitHub (é um único arquivo C, vá até a árvore de origem do arquivo de cabeçalho). Encontrei uma descrição da rotina em um grande livro sobre o Mathematica há muito tempo e uso variações dessa implementação há algum tempo. Basicamente, ele faz uma amostra linear aproximada sobre o domínio de interesse e depois refina regiões de alta curvatura. É possível que algumas características muito nítidas sejam perdidas, mas, na prática, acho isso extremamente raro. Este arquivo também contém a versão paralela.

Victor Liu
fonte
11
Que livro é esse? É o que eu vinculei? Você sabe o que exatamente muda na implementação entre as versões 5 e 6?
Szabolcs
11
@Szabolcs: Não, eu acredito que estava nesta seção do livro 4.1.3. A descrição aplica uma versão muito antiga do Mathematica. As versões mais recentes (talvez a partir da v6) detectam assíntotas verticais e removem as linhas verticais falsas das plotagens. As novas versões definitivamente fazem muito pré-processamento simbólico sofisticado para lidar com descontinuidades, regiões indefinidas e cortes de ramificações.
Victor Liu
O pré-processamento simbólico de que você está falando é chamado "detecção de exclusão" na documentação. Ele pode ser desativado por Exclusions -> Noneou ocultando a estrutura de sua função Plot, definindo-a como f[x_?NumericQ] := .... Não é disso que eu estava me referindo quando perguntei sobre as mudanças. Eu acredito que houve algumas mudanças no algoritmo, como v5 e v6 amostradas em pontos diferentes. No momento, não posso testar na v5 para comparar novamente.
Szabolcs
"O Guia de gráficos do Mathematica" continha uma discussão muito boa sobre o problema. Eu gostei especialmente que as falhas do algoritmo também foram descritas.
precisa saber é o seguinte
Não consigo mais encontrar o arquivo GitHub, ele foi movido?
Andrei
12

Saber como outros CAS fazem isso pode ajudá-lo.

Que eu saiba, o Mathematica usa uma variação no seguinte algoritmo básico para plotar uma função de uma variável ou uma curva paramétrica (vou assumir para esta descrição).( x ( t ) , y ( t ) ) f ( x )f(x)(x(t),y(t))f(x)

  1. Comece com uma grade de pontos regularmente espaçada no domínio de plotagem. Mat No Mathematica, há um parâmetro para controlar quantos levar, chamados PlotPoints.)

  2. Observe cada par de segmentos de linha sucessivos (definidos por três pontos sucessivos, ) e insira um novo ponto de amostragem no meio dos dois segmentos ( e ) se o ângulo for maior que um limite.x 1 + x 2(x1 1,f(x1 1)),(x2,f(x2)),(x3,f(x3))x1 1+x22x2+x32

  3. Se ainda não atingimos o limite de iteração (definido MaxRecursionno Mathematica), repita a partir da etapa 2.

Parte disso é discutida no livro Mathematica in Action, de Stan Wagon, que você pode ver aqui no Google Livros .

Eu implementei esse algoritmo antes para ter um melhor controle sobre quantas vezes minha função cara de calcular foi avaliada. Aqui está o código do Mathematica para a etapa 2:

nd[{points_, values_}] :=
Transpose@{(Drop[points, 1] + Drop[points, -1])/2,
Differences[values]/Differences[points]}

subdivide1d[result_, resolution_, maxAngle_: 10] :=
  Module[
    {deriv, angle, dangle, pos, nf},
    deriv = nd[result\[Transpose]];
    angle = ArcTan[#2] & @@@ deriv;
    dangle = Differences[angle];
    pos = Flatten@Position[dangle, d_ /; Abs[d] > maxAngle/180 Pi];
    pos = Union[pos, pos + 1];
    nf = Nearest[result[[All, 1]]];
    Select[deriv[[pos, 1]], Abs[# - First@nf[#]] > resolution &]
  ]
Szabolcs
fonte
7

A página do MathWorld na Web em Function Graphs contém referências a vários artigos que parecem relevantes na plotagem de funções adaptativas. Citando a página:

Boas rotinas para plotagem de gráficos usam algoritmos adaptativos que plotam mais pontos em regiões onde a função varia mais rapidamente (Wagon 1991, Math Works 1992, Heck 1993, Wickham-Jones 1994). Tupper (1996) desenvolveu um algoritmo [...]

Por outro lado, no Google me deparei com um artigo

www.cs.uic.edu/~wilkinson/Publications/plotfunc.pdf

que explica como escolher corretamente o domínio e outras coisas. Espero que sejam úteis para você.

astrojuanlu
fonte
1

Encontrei este tópico e achei que deveria compartilhar a página de problemas do desenvolvedor para adicioná-lo à biblioteca Julia Plots.jl. Tentamos várias técnicas para ver o que daria bons resultados, partindo das notas sobre a implementação do Mathematica. Adicionando alguma poda, uma pequena perturbação para não iniciar exatamente nos pontos finais do intervalo, um limite de recursão e um estimador de erro de malha dupla foram todos necessários para "acertar". O thread também indica o código-fonte aberto para a implementação. Por isso, foram necessários alguns ajustes, mas a adição desses recursos o tornou bastante robusto (de acordo com os testes, conforme mostrado no tópico).

Chris Rackauckas
fonte