Pergunta

No momento eu tenho um controle para que eu preciso adicionar a possibilidade de aplicar vários acuteness (ou sensibilidade). O problema é mais bem ilustrado como uma imagem:

Graph http://img87.imageshack.us/img87/7886/control. png

Como você pode ver, eu tenho X e Y Axess que ambos têm limites arbitrários de 100 - que deve ser suficiente para esta explicação. Neste momento, o meu controle é a linha vermelha (comportamento linear), mas eu gostaria de adicionar a capacidade para os outros 3 curvas (ou mais), ou seja, se um controle é mais sensível, em seguida, um ambiente irá ignorar a configuração linear e ir para um das três linhas. O ponto de partida será sempre 0, eo ponto final será sempre 100.

Eu sei que um exponencial é muito íngreme, mas não consigo descobrir uma maneira para a frente. Todas as sugestões agradar?

Foi útil?

Solução

As curvas de ter ilustrado olhar muito como correção de gama curvas. A idéia não é que o mínimo e máximo das estadias alcance o mesmo que o de entrada, mas o meio é dobrado como você tem em seus gráficos (que eu poderia notar é não o arco circular que você faria começa a partir da implementação cosseno).

Graficamente, ele se parece com isso:

text alt
(fonte: wikimedia.org )

Então, com isso como inspiração, aqui está a matemática ...

Se os seus valores x variou de 0 a 1, a função é bastante simples:

y = f(x, gamma) = x ^ gamma

Adicionar um valor xmax para escala (isto é, X = 0 a 100), e a função torna-se:

y = f(x, gamma) = ((x / xmax) ^ gamma) * xmax

ou, em alternativa:

y = f(x, gamma) = (x ^ gamma) / (xmax ^ (gamma - 1))

Você pode levar isso um passo adiante, se você quiser adicionar um xmin não-zero.

Quando gama é 1, a linha é sempre perfeitamente linear (y = x). Se x é inferior a 1, a sua curva se inclina para cima. Se x é maior que 1, a sua curva se inclina para baixo. O valor recíproco da gama vai converter o valor de volta para a origem (x = f (y, 1 / g) = f (f (x, g), 1 / g).

Apenas ajustar o valor de gamma de acordo com suas próprias necessidades gustativas e de aplicação. Desde que você está querendo dar ao usuário várias opções para "aumento de sensibilidade", você pode querer dar a seus usuários escolhas em uma escala linear, dizem que vão desde -4 (menos sensível) para 0 (sem mudança) a 4 (mais sensível ), e escalar seus valores de gama internos com uma função de potência. Em outras palavras, dar as escolhas do utilizador de (-4, -3, -2, -1, 0, 1, 2, 3, 4), mas que para traduzir valores de gama de (5,06, 3,38, 2,25, 1,50, 1,00 , 0,67, 0,44, 0,30, 0,20).

Coding que em C # pode ser algo como isto:

public class SensitivityAdjuster {
    public SensitivityAdjuster() { }
    public SensitivityAdjuster(int level) {
        SetSensitivityLevel(level);
    }
    private double _Gamma = 1.0;
    public void SetSensitivityLevel(int level) {
        _Gamma = Math.Pow(1.5, level);
    }
    public double Adjust(double x) {
        return (Math.Pow((x / 100), _Gamma) * 100);
    }
}

Para usá-lo, criar uma nova SensitivityAdjuster, definir o nível de sensibilidade de acordo com as preferências do usuário (usando o construtor ou o método, e -4 para 4 seria provavelmente valores nível razoável) e chamada Ajustar (x) para obter o valor de saída ajustada. Se você queria uma gama mais ampla ou mais estreita de níveis razoáveis, você iria reduzir ou aumentar esse valor 1,5 no método SetSensitivityLevels. E, claro, a 100 representa o seu valor máximo x.

Outras dicas

proponho uma fórmula simples, que (eu acredito) capta a sua exigência. A fim de ter um "quarto de círculo" completo, que é o seu caso extremo, você usaria (1-cos((x*pi)/(2*100)))*100.

O que eu sugiro é que você tome uma média ponderada entre y = x e y = (1-cos ((x * pi) / (2 * 100))) * 100. Por exemplo, para ter muito perto linear (99% linear), tomar:

y = 0.99*x + 0.01*[(1-cos((x*pi)/(2*100)))*100]

ou, mais geralmente, dizem que o nível de linearidade é L, e é no intervalo [0, 1], a fórmula será:

y = L*x + (1-L)*[(1-cos((x*pi)/(2*100)))*100]

EDIT: eu mudei cos(x/100) para cos((x*pi)/(2*100)), porque para os cos resultar estar no intervalo [1,0] X deve estar na faixa de [0, pi / 2] e não [0,1], desculpe o erro inicial.

Você está procurando provavelmente algo como polinomial interpolação . A interpolação quadrática / cúbica / quártica deve dar-lhe os tipos de curvas que você mostra na pergunta. As diferenças entre as três curvas que você mostra provavelmente poderia ser alcançado apenas ajustando os coeficientes (que indiretamente determinar inclinação).

O gráfico da y = x^p para x 0-1 irá fazer o que quiser como você variar p de 1 (o que dará a linha vermelha) para cima. Como p aumenta a curva será 'empurrado' mais e mais. p não tem que ser um inteiro.

(Você vai ter que escalar para obter 0 a 100 mas eu tenho certeza que você pode resolver isso)

Eu voto para a idéia geral de Rax Olgud, com uma modificação:

y = alpha * x + (1-alpha)*(f(x/100)*100)

alt texto http://www4c.wolframalpha.com / Calcular / MSP / MSP4501967d41e1aga1b3i00004bdeci2b6be2a59b? MSPStoreType = image / gif & s = 6

onde f (0) = 0, f (1) = 1, f (x) é superlinear, mas eu não sei de onde essa idéia "Círculo de um quarto" veio ou por 1-cos (x) seria uma boa escolha.

Eu sugiro f (x) = x k , onde k = 2, 3, 4, 5, o que quer que lhe dá a degre desejado de inclinação para o & alfa = 0. Escolha um valor para k como um número fixo, então variar a para escolher sua curva particular.

Para problemas como este, muitas vezes vai ter alguns pontos de uma curva e jogá-lo através de um programa de ajuste de curva. Há um monte deles lá fora. Aqui está um com um teste gratuito de 7 dias.

Eu aprendi muito ao tentar modelos diferentes. Muitas vezes você pode obter uma expressão muito simples para chegar perto de sua curva.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top