Copyright ©AlFrog 2000
Accueil Bios et drivers Palette des 216 couleurs      
Yam Perl - Aide mémoire Fractale de Mandelbrot      
La météo en Sarthe

Génération du fractale de Mandelbrot en Perl avec GD

Description et explications

Le fractale de Mandelbrot est sans doute le plus connu. Cependant, les explications concernant sa génération sont peu nombreuses. Sur cette page je vais tenter d'en expliquer les fondements théoriques. Vous trouverez un petit programme que j'ai écrit en Perl, utilisant la magnifique librairie GD pour la création de l'image, qui génère le fractale de Mandelbrot.

Télécharger Perl :
Pour Linux/Unix
Pour Windows - ActivePerl
Télécharger GD et documentation :
Recherche dans search.cpan.org

Le fractale de Mandelbrot est définit par une expression complexe, à savoir :
Z(n)=Z(n-1)²+C
où Z(n) et C sont des nombres complexes. On definit C=Re(C)+i*Im(C)=x+iy et Z(0)=0

Le fondement de l'exercice est relativement simple. Il s'agit d'étudier la convergence de la suite Z(n) pour tout point de coordonnées complexes (x,y).
On admet que la suite est convergente si à partir d'un certain rang n le module de Z(n) reste inférieur à 2. Dans ce cas, on va appliquer au point de coodonnées (x,y) un pixel de couleur noir.
Dans le cas où la suite diverge on va chercher le rang k pour lequel le module de Z(n) devient supérieur à 2 et appliquer au pixel une couleur correspondant au rang k.
Il parait donc judicieux de prévoir un rang limite qui ne soit pas trop élevé, pour diminuer le nombre d'itérations effectuées par le processeur, d'autant plus que visuellement on ne verra pas la différence (à cause des dimensions de l'image). Je me suis arrêté à 20 itérations, donc 20 couleurs, mais il est tout à fait possible d'aller beaucoup plus loin.

J'aurais bien mis une version paramètrable en ligne via les cgi avec Perl mais c'est mon hébergeur qui tirerait la tronche. Les temps de calculs sont un peu longs et je n'ai pas envie de saturer le server d'un hébergeur gratuit.


La source du programme

mandel.pl

#!/usr/bin/perl

print "Content-type: image/png\n\n";

# on a besoin du module perl GD
use GD;

# création du fichier image mandel.png
open(OUTF,">mandel.png") || return 1;

# def hauteur et largeur de l'image
$w=450;
$h=375;

# def du nombre d'itérations (idem nombre de couleurs)
$n=20;

# create a new image
$im = new GD::Image($w,$h);

# allocation de couleurs
$white = $im->colorAllocate(255,255,255);
$black = $im->colorAllocate(0,0,0);
# tirage aléatoire $color1...$n
for($i=1;$i<($n+1);$i++)
{
  $tmp='$color'.$i.'= $im->colorAllocate('.int(rand(256)).','.int(rand(256)).','.int(rand(256)).');';
  eval $tmp;
}

# parcour de la zone de pixels
for($x=0;$x<$w;$x++)
{
  for($y=0;$y<$h;$y++)
  {
    # def du nb complexe C en fonction de (x,y)
    $reC=($x-3*$w/4)/($w/3); # centrage horizontal de l'image
    $imC=($y-$h/2)/($w/3); # centrage vertical de l'image
    # def du nb complexe Z(0)=0
    $rez=0;
    $imz=0;

    # recherche de la couleur du pixel étudié
    $color=0;
    $test=0;
    while($test==0)
    {
      $old_rez=$rez; # sauvegarde de Re(Zn-1)
      $rez=$rez*$rez-$imz*$imz+$reC;
      $imz=2*$old_rez*$imz+$imC;
      $color++;
      if(($rez*$rez+$imz*$imz)>4)
      {
        $test=1;
        $div=1;
      }
      elsif($color==$n)
      {
        $test=1;
        $div=0;
      }
    }
    # Affichage du pixel
    if($div==0)
    {
      $im->setPixel($x,$y,$black);
    }
    else
    {
      $tmp='$im->setPixel($x,$y,$color'.$color.');';
      eval $tmp;
    }
    }
}

binmode (OUTF);
print OUTF $im->png;
close(OUTF);


Résultat

mandel.png - Nombre d'itérations : 20, Xmin= -2.25, Xmax= 0.75, Ymin= -1.5, Ymax= 1.5