Question

Je viens de terminer deuxième année à l'Uni faisant un cours de jeu, ce qui est toujours été mise sur écoute-moi comment sont liés aux mathématiques et à la programmation de jeux. Jusqu'à présent, je me sers Vectors, Matrices et Quaternions dans les jeux, je peux en position comment ceux-ci se intégrer dans les jeux.

Ceci est un General Question sur la relation entre les mathématiques et la programmation graphique en temps réel, je suis curieux de savoir sur la façon dynamique les mathématiques est. Est-ce un cas où toutes les formules et les dérivés sont prédéfinies (semi-définis)?

Est-il même possible de calculer des dérivées en temps réel / Intégrales?

Voici quelques-unes des choses que je ne vois pas comment ils se programmation à l'intérieur / mathématiques À titre d'exemple.

  1. MacLaurin/Talor Series Je peux voir ce qui est utile, mais est-ce le cas que vous devez passer votre fonction et de ses dérivés, ou pouvez-vous transmettre une seule fonction et le faire fonctionner les dérivés pour vous?

    MacLaurin(sin(X)); or MacLaurin(sin(x), cos(x), -sin(x));
    
  2. Derivatives /Integrals Ceci est lié au premier point. Calcul de la y' d'une fonction fait dynamiquement au moment de l'exécution ou est-ce quelque chose qui est peut-être fait statiquement avec des variables dans une fonction de jeu.

    f = derive(x); or f = derivedX;
    
  3. Bilnear Patches Nous avons appris cela comme un moyen de générer des paysages possible en petits morceaux qui pourraient être « Sewen » ensemble, est-ce quelque chose qui se passe dans les jeux? Je ne l'ai jamais entendu parler de cela (exaucé mes knowlages est très limité) utilisé avec des méthodes de procédure ou autrement. Ce que je l'ai fait ce jour consiste à des réseaux pour les informations de sommet étant processesed.

Désolé si cela est hors sujet, mais la communauté semble ici sur place, sur ce genre de chose.

Merci.

Était-ce utile?

La solution

La réponse de Skizz est vrai, pris littéralement, mais seulement un petit changement est nécessaire pour permettre de calculer la dérivée d'une fonction C ++. Nous modifions la fonction de Skizz f à

template<class Float> f (Float x)
{
  return x * x + Float(4.0f) * x + Float(6.0f); // f(x) = x^2 + 4x + 6
}

Il est maintenant possible d'écrire une fonction C ++ pour calculer la dérivée de f par rapport à x. Voici un programme autonome complète pour calculer la dérivée de f. Il est exact (à la précision de la machine) car il ne l'utilise une méthode imprécise comme des différences finies. J'explique comment cela fonctionne dans un papier je l'ai écrit. Il généralise aux dérivés supérieurs. Notez que beaucoup de travail est fait statiquement par le compilateur. Si vous mettez en place l'optimisation et vos inline du compilateur décemment, il doit être aussi rapide que tout ce que vous pouvez écrire à la main pour des fonctions simples. (Parfois plus vite! En particulier, il est tout à fait bon à amortissant le coût de calcul f et f 'en même temps, car il rend l'élimination des sous-expression commune plus facile pour le compilateur à repérer que si vous écrivez des fonctions distinctes pour f et f.)

using namespace std;

template<class Float>
Float f(Float x)
{
  return x * x + Float(4.0f) * x + Float(6.0f);
}

struct D
{
  D(float x0, float dx0 = 0) : x(x0), dx(dx0) { }
  float x, dx;
};

D operator+(const D &a, const D &b)
{
  // The rule for the sum of two functions.
  return D(a.x+b.x, a.dx+b.dx);
}

D operator*(const D &a, const D &b)
{
  // The usual Leibniz product rule.
  return D(a.x*b.x, a.x*b.dx+a.dx*b.x);
}

// Here's the function skizz said you couldn't write.
float d(D (*f)(D), float x) {
  return f(D(x, 1.0f)).dx;
}

int main()
{
  cout << f(0) << endl;
  // We can't just take the address of f. We need to say which instance of the
  // template we need. In this case, f<D>.
  cout << d(&f<D>, 0.0f) << endl;
}

Il imprime les résultats et 6 4 que vous devriez vous attendre. Essayez d'autres fonctions f. Un bon exercice est d'essayer de travailler les règles pour permettre la soustraction, division, fonctions trigonométriques etc.

Autres conseils

2) Instruments dérivés et ne sont généralement pas Intégrales calculés sur de grands ensembles de données en temps réel, son trop cher. Au contraire, ils sont précalculées. Par exemple (en haut de ma tête) pour rendre une seule dispersion des médias Bo Sun et al. utiliser leur « modèle airlight » qui se compose d'un grand nombre de raccourcis algébriques pour obtenir une table de consultation précalculées.

3) en streaming grands ensembles de données est un sujet important, surtout en terrain.

Beaucoup de mathématiques que vous rencontrerez dans les jeux est de résoudre des problèmes très spécifiques, et est généralement maintenu simple. algèbre linéaire est utilisée beaucoup plus que tout calcul. Dans Graphics (je aime ce le plus) beaucoup des algorithmes proviennent de recherches effectuées dans le milieu universitaire, puis ils sont modifiés pour la vitesse par des programmeurs de jeu. Bien que ces jours accélèrent leur objectif de recherche, même marques académiques

Je recommande les deux livres de détection de collision en temps réel et le rendu en temps réel, qui contiennent les entrailles de la plupart des mathématiques et des concepts utilisés dans la programmation du moteur de jeu.

Je pense qu'il ya un problème fondamental avec votre compréhension du langage C ++ lui-même. Fonctions en C ++ ne sont pas les mêmes que les fonctions mathmatical. Ainsi, en C ++, vous pouvez définir pour mettre en œuvre une fonction mathmatical une fonction (que je vais appeler des méthodes pour éviter toute confusion):

float f (float x)
{
  return x * x + 4.0f * x + 6.0f; // f(x) = x^2 + 4x + 6
}

En C ++, il n'y a aucun moyen de faire quoi que ce soit avec la méthode f autre que pour obtenir la valeur de f (x) pour un x donné. La fonction mathmatical f (x) peut être transformé facilement, f « (x) par exemple, qui, dans l'exemple ci-dessus est f » (x) = 2x + 4. Pour ce faire, en C ++, vous aurez besoin de définir une méthode df (x):

float df (float x)
{
  return 2.0f * x + 4.0f; //  f'(x) = 2x + 4
}

vous ne pouvez pas faire ceci:

get_derivative (f(x));

et ont la méthode get_derivative transformer la méthode f (x) pour vous.

En outre, vous devez faire en sorte que lorsque vous vouliez la dérivée de f que vous appelez la méthode df. Si vous avez appelé la méthode de la dérivée de g par hasard, vos résultats seraient mauvais.

On peut cependant approcher la dérivée de f (x) pour un x donné:

float d (float (*f) (float x), x) // pass a pointer to the method f and the value x
{
  const float epsilon = a small value;
  float dy = f(x+epsilon/2.0f) - f(x-epsilon/2.0f);
  return epsilon / dy;
}

mais cela est très instable et tout à fait inexact.

Maintenant, en C ++, vous pouvez créer une classe d'aide ici:

class Function
{
public:
  virtual float f (float x) = 0; // f(x)
  virtual float df (float x) = 0; // f'(x)
  virtual float ddf (float x) = 0; // f''(x)
  // if you wanted further transformations you'd need to add methods for them
};

et créer notre propre fonction mathmatical:

class ExampleFunction : Function
{
  float f (float x) { return x * x + 4.0f * x + 6.0f; } // f(x) = x^2 + 4x + 6 
  float df (float x) { return 2.0f * x + 4.0f; } //  f'(x) = 2x + 4
  float ddf (float x) { return 2.0f; } //  f''(x) = 2
};

et transmettre une instance de cette classe dans un sous-programme de développement en série:

float Series (Function &f, float x)
{
   return f.f (x) + f.df (x) + f.ddf (x); // series = f(x) + f'(x) + f''(x)
}

mais nous sommes encore avoir à créer une méthode pour on ne va pas appeler accidentellement la fonction nous dérivée de, mais au moins le mauvais.

Maintenant, comme d'autres l'ont dit, les jeux ont tendance à favoriser la vitesse, donc beaucoup des mathématiques est simplifiée:. Interpolation, tables pré-calculées, etc

La plupart des mathématiques dans les jeux est conçu pour comme pas cher pour calculer que possible, la vitesse de négociation sur la précision. Par exemple, une grande partie du nombre crissement utilise des nombres entiers ou simple précision flotte plutôt que double.

Je ne sais pas sur vos exemples spécifiques, mais si vous pouvez définir un pas cher (à calculer) formule un préalable dérivé, puis qui est préférable de calculer les choses à la volée.

Dans les jeux, la performance est primordiale. Vous ne trouverez pas tout ce qui est fait de façon dynamique quand il pourrait être fait de manière statique, à moins que cela conduit à une augmentation notable de la fidélité visuelle.

Vous pourriez être intéressé par la compilation différenciation symbolique. Cela peut (en principe) être fait avec c ++ modèles. Aucune idée quant à savoir si les jeux font dans la pratique (la différenciation symbolique peut-être trop cher à droite du programme et une telle utilisation intensive du modèle pourrait être trop coûteux en temps de compilation, je ne sais pas).

Cependant, je pensais que vous pourriez trouver la discussion de ce sujet intéressant. Googler "c ++ modèle dérivé symbolique" donne quelques articles.

Il y a beaucoup de grandes réponses si vous êtes intéressé par le calcul symbolique et calcul des dérivés.

Cependant, tout comme un contrôle de santé mentale, ce genre de calcul symbolique (analytique) n'est pas pratique de le faire en temps réel dans le contexte des jeux.

Dans mon expérience (qui est plus géométrie 3D en vision par ordinateur que les jeux), la plupart du calcul et en mathématiques en géométrie 3D vient par des choses hors ligne de calcul à l'avance et de codage pour mettre en œuvre ce calcul. Il est très rare que vous aurez besoin de choses symboliquement calcul à la volée, puis prendre à la volée des formules analytiques ainsi.

Peut-programmeurs de jeu vérifier?

1), 2)

série de Maclaurin / Taylor (1) sont construits à partir des dérivés (2) dans tous les cas.

Oui, il est rare de besoin de calculer symboliquement l'un de ces à l'exécution - mais sûr user207442 » s réponse est bien si vous en avez besoin.

Qu'est-ce que vous trouvez que vous devez effectuer un calcul mathématique et que vous avez besoin de le faire dans un délai raisonnable, ou parfois très rapide. Pour ce faire, même si vous êtes à usage d'autres solutions pour, vous aurez besoin de comprendre l'analyse de base.

Si vous devez résoudre le problème vous-même, est à l'envers que vous souvent besoin d'une réponse approximative. Cela signifie que, par exemple, une extension de type série pourrait bien vous permettre de réduire une fonction complexe à un linéaire simple ou quadratique, qui sera très rapide.

Pour Intégrales, l'on peut souvent calculer le résultat numériquement, mais il sera toujours beaucoup plus lent que d'une solution analytique. La différence pourrait bien être la différence entre être pratique ou non.

En bref: Oui, vous avez besoin d'apprendre les mathématiques, mais pour écrire le programme plutôt que d'avoir le programme le faire pour vous

.
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top