<?xml version="1.0" encoding="utf-8"?><?xml-stylesheet title="XSL formatting" type="text/xsl" href="http://www.code-web.org/feed/rss2/xslt" ?><rss version="2.0"
  xmlns:dc="http://purl.org/dc/elements/1.1/"
  xmlns:wfw="http://wellformedweb.org/CommentAPI/"
  xmlns:content="http://purl.org/rss/1.0/modules/content/">
<channel>
  <title>Code-Web.org - objet</title>
  <link>http://www.code-web.org/</link>
  <description>Développement Web en toute liberté!</description>
  <language>fr</language>
  <pubDate>Mon, 08 Sep 2008 10:48:53 +0200</pubDate>
  <copyright></copyright>
  <docs>http://blogs.law.harvard.edu/tech/rss</docs>
  <generator>Dotclear</generator>
  
    
  <item>
    <title>Getter et setter automatiques avec les méthodes magiques sous PHP 5</title>
    <link>http://www.code-web.org/post/2008/05/13/Les-methodes-magic-sous-PHP-5</link>
    <guid isPermaLink="false">urn:md5:e2966caeb7bac628255e8704e274f59e</guid>
    <pubDate>Tue, 13 May 2008 17:17:00 +0200</pubDate>
    <dc:creator>Thierry Geindre</dc:creator>
        <category>PHP</category>
        <category>objet</category><category>php</category>    
    <description>&lt;p&gt;L' objet sous PHP 5 introduit de nouvelles methodes, dites magiques. Elles permettent de s'affranchir de tâches parfois fastidieuses telles que l'écriture de getter et de setter. Nous allons voir comment employer deux de ces méthodes.&lt;/p&gt;    &lt;p&gt;L'un des avantages de l'objet est la possibilité d'en capsuler les données dans un objet et ainsi de pouvoir exercer un certain contrôle sur les accès qui sont effectués. Cependant, lorsque ces données deviennent nombreuses, l'écriture de toutes les méthodes d'accès peut devenir fastidieuse. Prenons un exemple assez simple&amp;nbsp;:&lt;/p&gt;
&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;class&lt;/span&gt; foo&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$a&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$b&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$c&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#91;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;...&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#93;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$z&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;&lt;/pre&gt;

&lt;p&gt;Il nous faudrait, en principe, pas moins de 26 getter et 26 setter (soit 52 méthodes) pour pouvoir accéder à tous les attributs de cette classe. Il existe bien des outils qui permettent l'écriture automatisée des ces méthodes, mais on assistera alors à une belle surcharge de code.&lt;/p&gt;


&lt;p&gt;C'est là qu'interviennent les méthodes &lt;strong&gt;__get()&lt;/strong&gt; et &lt;strong&gt;__set()&lt;/strong&gt;.&lt;/p&gt;


&lt;h3&gt;La méthode __set()&lt;/h3&gt;

&lt;p&gt;Cette méthode reçoit deux paramètres, le nom de l'attribut auquel on souhaite accéder et la valeur que l'on souhaite lui donner. Reprenons donc avec notre exemple de classe&amp;nbsp;:&lt;/p&gt;

&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;class&lt;/span&gt; foo&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$a&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$b&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$c&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#91;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;...&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#93;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$z&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&amp;nbsp;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;public&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; __set&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$attr&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$value&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
   &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
       &lt;span style=&quot;color: #b1b100;&quot;&gt;if&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #000066;&quot;&gt;isset&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$this&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$attr&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$this&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$attr&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$value&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
       &lt;span style=&quot;color: #b1b100;&quot;&gt;else&lt;/span&gt; throw &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;new&lt;/span&gt; Exception&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000;&quot;&gt;'Unknow attribute '&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;.&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$attr&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;&lt;/pre&gt;

&lt;p&gt;Si l'attribut demandé n'existe pas, on lance une exception.&lt;/p&gt;


&lt;h3&gt;La méthode __get()&lt;/h3&gt;

&lt;p&gt;Cette méthode ne reçoit qu'un seul paramètre, c'est le nom de l'attribut qui a été appelé. Reprenons donc avec notre exemple de classe&amp;nbsp;:&lt;/p&gt;
&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;class&lt;/span&gt; foo&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$a&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$b&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$c&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#91;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;...&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#93;&lt;/span&gt;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$z&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&amp;nbsp;
   &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;public&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; __get&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$attr&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
   &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
      &lt;span style=&quot;color: #b1b100;&quot;&gt;if&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #000066;&quot;&gt;isset&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$this&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$attr&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt; &lt;span style=&quot;color: #b1b100;&quot;&gt;return&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$this&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$attr&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
      &lt;span style=&quot;color: #b1b100;&quot;&gt;else&lt;/span&gt; throw &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;new&lt;/span&gt; Exception&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000;&quot;&gt;'Unknow attribute '&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;.&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$attr&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
   &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;&lt;/pre&gt;

&lt;p&gt;Si l'attribut demandé n'existe pas, on lance une exception.&lt;/p&gt;


&lt;h3&gt;Réinventons &lt;em&gt;stdclass&lt;/em&gt;&lt;/h3&gt;

&lt;p&gt;&lt;em&gt;Stdclass&lt;/em&gt; est une classe définit par php. Elle permet de stocker autant d'attributs que l'on souhaite. Il est donc possible d'écrire le code suivant sans aucun problème&amp;nbsp;:&lt;/p&gt;
&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$a&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;new&lt;/span&gt; stdclass&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&lt;span style=&quot;color: #ff0000&quot;&gt;$a&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;foo&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #cc66cc;&quot;&gt;10&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&lt;span style=&quot;color: #000066;&quot;&gt;echo&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$a&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;foo&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt; &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Affiche bien 10&lt;/span&gt;&lt;/pre&gt;

&lt;p&gt;Voici donc, à partir de ce que nous venons de voir, de quelle manière nous pourrions implémenter une telle classe. Pour éviter les conflits, nous la nommerons &lt;em&gt;MyStdclass&lt;/em&gt;&amp;nbsp;:&lt;/p&gt;
&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;class&lt;/span&gt; MyStdclass
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
  &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$data&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&amp;nbsp;
  &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;public&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; __construct&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
  &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
    &lt;span style=&quot;color: #ff0000&quot;&gt;$this&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;data&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000066;&quot;&gt;array&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
  &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
  &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;public&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; __set&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$key&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;,&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$value&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
  &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
    &lt;span style=&quot;color: #ff0000&quot;&gt;$this&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;data&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#91;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$key&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#93;&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$value&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
  &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
  &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;public&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; __get&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$key&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
  &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
    &lt;span style=&quot;color: #b1b100;&quot;&gt;return&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$this&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;data&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#91;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$key&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#93;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
  &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;&lt;/pre&gt;

&lt;p&gt;Je ne lance pas d'erreur ici, logiquement PHP s'en chargera selon sa configuration, comportement adopté par &lt;em&gt;stdclass&lt;/em&gt;. Mais rien n'empêche de lancer des erreurs en cas d'attribut indéfini.&lt;/p&gt;


&lt;h3&gt;Conclusion&lt;/h3&gt;

&lt;p&gt;Personnellement, l'emploi d'un tableau me parait plus propre plutôt que de définir de nouveau attribut. Un tableau est une structure naturellement dynamique en PHP et on sait que, quoi qu'il contienne, il conservera toujours la même visibilité. Quel est la visibilité de nouveaux attributs définit durant l'exécution? Bonne question, &lt;em&gt;public&lt;/em&gt; j'imagine...&lt;/p&gt;


&lt;p&gt;J'en ai déjà vu certains dire (ou plutôt écrire) que l'utilisation de tableaux rendait les écritures moins simples dans les méthodes. &lt;strong&gt;Oui mais&lt;/strong&gt;, le fait de définir les méthodes __get() et __set() tel qu'indiqué ci-dessus, rend possible l'emploi de $this-&amp;gt;indiceDuTableau, les écritures restent donc rigoureusement les mêmes qu'avec des attributs classiques.&lt;/p&gt;</description>
    
    
    
          <comments>http://www.code-web.org/post/2008/05/13/Les-methodes-magic-sous-PHP-5#comment-form</comments>
      <wfw:comment>http://www.code-web.org/post/2008/05/13/Les-methodes-magic-sous-PHP-5#comment-form</wfw:comment>
      <wfw:commentRss>http://www.code-web.org/feed/rss2/comments/48</wfw:commentRss>
    						<h3>Abonnement aux commentaires</h3>
						<p>
							<a href="http://www.code-web.org/subscribetocomments?post_id=48">
								<!-- # If the subscriber is logged in -->
																<!-- # If the subscriber is not logged in -->
																	S'abonner pour recevoir les commentaires suivants par email															</a>
						</p>
					  </item>
    
  <item>
    <title>Un singleton en PHP</title>
    <link>http://www.code-web.org/post/2007/11/12/23-un-singleton-en-php</link>
    <guid isPermaLink="false">urn:md5:aab7ebfdbdac828cd62a7f5635995f09</guid>
    <pubDate>Mon, 12 Nov 2007 11:28:00 +0000</pubDate>
    <dc:creator>Thierry Geindre</dc:creator>
        <category>PHP</category>
        <category>objet</category><category>php</category>    
    <description>&lt;p&gt;Nous parlerons ici de développement orienté objet avec PHP. En effet, un singleton est ce que l'on appel un design pattern (comprenez&amp;nbsp;: motif de conception) qui n'est applicable qu'à des classes et objets. Nous verrons ce qu'est exactement un singleton puis nous verrons comment procéder en PHP5 pour le mettre en place. Enfin, nous étudierons comment procéder en PHP4, version du langage pour laquelle les choses sont un peu différentes.&lt;/p&gt;    &lt;h3&gt;Définition et intérêts du singleton&lt;/h3&gt;

&lt;p&gt;Un singleton est un motif de conception pour une classe. Il permet de limiter l'instanciation de la classe à un seul et unique objet. Il ne pourra donc pas être créé plus d'une seule instance de la classe en question.&lt;/p&gt;


&lt;p&gt;Ce genre de classe pourra être utilisée, par exemple, pour les accès à une base de données. Elle permettra d'empêcher toute nouvelle connexion inutile au SGBD. D'autre part, les singleton peuvent aussi régler les problèmes de visibillité de certaines variables. En effet il n'est plus nécessaire de conserver et de transmettre un référence vers l'instance. Il est toujours possible via une méthode statique de récupérer la dernière instance créée, ou, s'il n'y a aucune instance créée, d'en créer une nouvelle.&lt;/p&gt;


&lt;h3&gt;Singleton en PHP5&lt;/h3&gt;

&lt;p&gt;PHP5 fournit tout les éléments dont nous aurons besoin pour la mise en œuvre d'un singleton. Nous utiliserons, entre autres, un attribut statique et la méthode __clone() qui permet de détecter la création d'une seconde (et plus) instance.&lt;/p&gt;

&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;&amp;lt;?php&lt;/span&gt;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;class&lt;/span&gt; Singleton
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
    &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// instance de la classe&lt;/span&gt;
    &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #000066;&quot;&gt;static&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&amp;nbsp;
    &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// On utilise un constructeur privé pour empêcher&lt;/span&gt;
    &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// la création d'instance directe&lt;/span&gt;
    &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;private&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; __construct&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt; 
    &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
        &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Code à la construction...&lt;/span&gt;
    &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
    &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// La méthode singleton&lt;/span&gt;
    &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// permet de récupérer/créer une instance&lt;/span&gt;
    &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;public&lt;/span&gt; &lt;span style=&quot;color: #000066;&quot;&gt;static&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt; 
    &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
        &lt;span style=&quot;color: #b1b100;&quot;&gt;if&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;!&lt;/span&gt;&lt;span style=&quot;color: #000066;&quot;&gt;isset&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;self&lt;span style=&quot;color: #66cc66;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
            &lt;span style=&quot;color: #ff0000&quot;&gt;$className&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;__CLASS__&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
            self&lt;span style=&quot;color: #66cc66;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;new&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$className&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
        &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
        &lt;span style=&quot;color: #b1b100;&quot;&gt;return&lt;/span&gt; self&lt;span style=&quot;color: #66cc66;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
    &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
    &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Interdit le clonage de l'objet&lt;/span&gt;
    &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// pas plus d'une instance n'est permise&lt;/span&gt;
    &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;public&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; __clone&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
    &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
        &lt;span style=&quot;color: #000066;&quot;&gt;trigger_error&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000;&quot;&gt;'Le clônage n&lt;span style=&quot;color: #000099; font-weight: bold;&quot;&gt;\'&lt;/span&gt;est pas autorisé.'&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;,&lt;/span&gt;
            &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;E_USER_ERROR&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
    &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;?&amp;gt;&lt;/span&gt;&lt;/pre&gt;

&lt;p&gt;Une fois qu'une classe est déclarée ainsi, il sera possible d'appeler à n'importe quel moment dans votre code l'instance correspondante (ou créée au besoin) via ce code&amp;nbsp;:&lt;/p&gt;
&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$mySingleton&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;singleton&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;&lt;/pre&gt;


&lt;p&gt;Il suffira donc de faire un appel statique sur la méthode singleton() de votre classe.&lt;/p&gt;


&lt;p&gt;Je vous rappel que la méthode utilisée ici pour la mise en œuvre du singleton ne fonctionne qu'à partir de PHP5. Elle ne fonctionnera donc pas en PHP4 et pour cause&amp;nbsp;: les attributs statiques n'existent pas, pas plus que la méthode __clone() (elle serait considérée comme une méthode classique).&lt;/p&gt;


&lt;h3&gt;Singleton en PHP4&lt;/h3&gt;


&lt;p&gt;Comme je le disais, les attributs statiques n'existent pas en PHP4. N'y la méthode __clone() d'ailleurs. Cependant nous allons pouvoir utiliser le mot clé &lt;strong&gt;static&lt;/strong&gt; de PHP4 disponible dans une fonction ou une méthode (qui n'est rien d'autre qu'une fonction membre, donc une fonction...). Ce mot clé permet de déclarer des variables locales (dans la fonction uniquement) de façon durable. Un exemple sera plus parlant&amp;nbsp;:&lt;/p&gt;

&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;&amp;lt;?php&lt;/span&gt;
&amp;nbsp;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; getI&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
      &lt;span style=&quot;color: #000066;&quot;&gt;static&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$i&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #cc66cc;&quot;&gt;0&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
      &lt;span style=&quot;color: #b1b100;&quot;&gt;return&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;++&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$i&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
&lt;span style=&quot;color: #000066;&quot;&gt;echo&lt;/span&gt; getI&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt; &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Affiche 1&lt;/span&gt;
&lt;span style=&quot;color: #000066;&quot;&gt;echo&lt;/span&gt; getI&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt; &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Affiche 2&lt;/span&gt;
&lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// on conserve la valeur de $i d'un appel à l'autre&lt;/span&gt;
&amp;nbsp;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;?&amp;gt;&lt;/span&gt;&lt;/pre&gt;


&lt;p&gt;Il nous sera donc possible, dans notre classe, de conserver une référence vers l'instance. Le singleton va donc pouvoir être créé! Et voici comment&amp;nbsp;:&lt;/p&gt;

&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;&amp;lt;?php&lt;/span&gt;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;class&lt;/span&gt; Singleton
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
      &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Constructeur, impossible de le passer privé en PHP4&lt;/span&gt;
      &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$fromGetInstance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;false&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
      &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
            &lt;span style=&quot;color: #b1b100;&quot;&gt;if&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;!&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$fromGetInstance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
                &lt;span style=&quot;color: #000066;&quot;&gt;die&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #ff0000;&quot;&gt;&amp;quot;Erreur, instanciation directe non permise.&amp;quot;&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
            &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// suite des instructions&lt;/span&gt;
      &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
      &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Méthode d'obtention de l'instance&lt;/span&gt;
      &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;amp;&lt;/span&gt;getInstance&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
      &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
            &lt;span style=&quot;color: #000066;&quot;&gt;static&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;null&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
            &lt;span style=&quot;color: #b1b100;&quot;&gt;if&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;==&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;null&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt; 
                &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;new&lt;/span&gt; Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;true&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
            &lt;span style=&quot;color: #b1b100;&quot;&gt;return&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
      &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;?&amp;gt;&lt;/span&gt;&lt;/pre&gt;


&lt;p&gt;Comme vous pouvez le voir, nous avons rajouté un paramètre au constructeur afin d'interdire la construction directe d'objet, c'est à dire sans passer par la méthode getInstance(). Cependant, il est toujours possible de créer une instance librement en passant au constructeur la valeur true. En PHP4, il faut ruser puisqu'il est impossible de déclarer une méthode, constructeur ou pas, privée.&lt;/p&gt;


&lt;p&gt;Il existe une solution qui consiste à profiter du fait que PHP ne permet pas la déclaration de deux constantes ou fonctions portant le même nom. Personnellement je ne suis pas très satisfait par cette méthode. En effet elle impose de définir inutilement une fonction ou une constante qui pourrait éventuellement interférer avec le reste du script. Je vous propose toutefois de découvrir cette méthode dans &lt;a href=&quot;http://zefredz.frimouvy.org/dotclear/index.php?2007/02/18/160-forcer-un-singleton-en-php4&quot; hreflang=&quot;fr&quot;&gt;un autre article traitant des singletons en PHP&lt;/a&gt;.&lt;/p&gt;


&lt;p&gt;Et je vous propose ici la méthode que j'ai mis au point permettant d'interdire tout passage directe par le constructeur pour l'instanciation de la classe. J'avoue que le système que je vais vous expliquer est quelque peu alambiqué. Mais, ne l'oublions pas, nous sommes en PHP et les solutions simples n'existent pas toujours compte tenu des outils mis à notre disposition.&lt;/p&gt;


&lt;p&gt;On sait qu'il est possible de définir plusieurs variables locales statiques dans une fonction ou méthode. En plus de notre référence vers l'instance, on pourra donc créer une autre variable statique dans la méthode getInstance(). D'autre part, il est possible de passer des paramètres à la méthode getInstance(), comme à tout autre méthode. Sachant cela, nous allons pouvoir définir deux comportements différents pour la méthode getInstance() en fonction de la valeur d'un paramètre.&lt;/p&gt;


&lt;p&gt;Rajoutons un paramètre à la méthode getInstance(). Il s'agit d'un booléen permettant de modifier le comportement de la méthode. On déclarera donc notre méthode ainsi&amp;nbsp;:&lt;/p&gt;

&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;&amp;lt;?php&lt;/span&gt;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;amp;&lt;/span&gt;getInstance&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$testConstruct&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;false&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
&lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// [...]&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;?&amp;gt;&lt;/span&gt;&lt;/pre&gt;


&lt;p&gt;Le paramètre est optionnel et par défaut a pour valeur false. L'utilisation classique pour obtenir l'instance ne change donc pas. Par conséquent, la méthode getInstance() conservera presque le même comportement lorsque ce paramètre a pour valeur false. En revanche, s'il a pour valeur true, la méthode doit être en mesure de répondre si elle à bien demandé une nouvelle instance au moyen d'un booléen qu'elle renverra. Ainsi, le constructeur pourra appeler cette méthode pour vérifier que l'instanciation est autorisée, sans quoi il renverra une erreur.&lt;/p&gt;


&lt;p&gt;Ce n'est peut être pas encore clair. Mais voici quand même le résultat de toutes ces explications&amp;nbsp;:&lt;/p&gt;

&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;&amp;lt;?php&lt;/span&gt;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;class&lt;/span&gt; Singleton
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
      &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Constructeur, impossible de le passer privé en PHP4&lt;/span&gt;
      &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
      &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
            &lt;span style=&quot;color: #b1b100;&quot;&gt;if&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;!&lt;/span&gt;Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;getInstance&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;true&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
                &lt;span style=&quot;color: #000066;&quot;&gt;die&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #ff0000;&quot;&gt;&amp;quot;Erreur, instanciation directe non permise.&amp;quot;&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
            &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// suite des instructions&lt;/span&gt;
      &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&amp;nbsp;
      &lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Méthode d'obtention de l'instance&lt;/span&gt;
      &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;function&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;amp;&lt;/span&gt;getInstance&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$testConstruct&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;false&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
      &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
            &lt;span style=&quot;color: #000066;&quot;&gt;static&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;null&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;,&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$testInit&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;false&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&amp;nbsp;
            &lt;span style=&quot;color: #b1b100;&quot;&gt;if&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;!&lt;/span&gt;&lt;span style=&quot;color: #ff0000&quot;&gt;$testConstruct&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
            &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
                  &lt;span style=&quot;color: #b1b100;&quot;&gt;if&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;==&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;null&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;
                  &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#123;&lt;/span&gt;
                        &lt;span style=&quot;color: #ff0000&quot;&gt;$testInit&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;true&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
                        &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;new&lt;/span&gt; Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;true&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
                        &lt;span style=&quot;color: #ff0000&quot;&gt;$testInit&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;false&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
                  &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
                  &lt;span style=&quot;color: #b1b100;&quot;&gt;return&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$instance&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
            &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
            &lt;span style=&quot;color: #ff0000&quot;&gt;$dc&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$testInit&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
            &lt;span style=&quot;color: #b1b100;&quot;&gt;return&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$dc&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
      &lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#125;&lt;/span&gt;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;?&amp;gt;&lt;/span&gt;&lt;/pre&gt;


&lt;p&gt;Lorsque l'on appel la méthode getInstance() pour la première fois, celle-ci change la valeur du booléen $testInit pour true puis créée une nouvelle instance de la classe singleton. Le constructeur de la classe est alors appelé, il appel lui même la méthode getInstance() avec le paramètre $testConstruct à true. Cette méthode va alors lui retourner la valeur de $testInit qui aura pour valeur true signifiant que l'instanciation de la classe à bien été demandée par la méthode getInstace(). Une fois l'instance créée, la méthode getInstance(), initialement appelée, remet le booléen $testInit à false. Ainsi tout appel au constructeur aboutira forcément sur un échec.&lt;/p&gt;


&lt;p&gt;Vous pouvez tester cette classe avec le code suivant&amp;nbsp;:&lt;/p&gt;

&lt;pre class=&quot;php&quot;&gt;&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;&amp;lt;?php&lt;/span&gt;
&lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Nouvelle instance&lt;/span&gt;
&lt;span style=&quot;color: #ff0000&quot;&gt;$a&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&amp;amp;&lt;/span&gt; Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;getInstance&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&lt;span style=&quot;color: #ff0000&quot;&gt;$a&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;i&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #cc66cc;&quot;&gt;10&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&amp;nbsp;
&lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Récupération de l'instance&lt;/span&gt;
&lt;span style=&quot;color: #ff0000&quot;&gt;$b&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&amp;amp;&lt;/span&gt; Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;::&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;getInstance&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Affiche bien 10&lt;/span&gt;
&lt;span style=&quot;color: #000066;&quot;&gt;echo&lt;/span&gt; &lt;span style=&quot;color: #ff0000&quot;&gt;$b&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;-&amp;gt;&lt;/span&gt;&lt;span style=&quot;color: #006600;&quot;&gt;i&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&amp;nbsp;
&lt;span style=&quot;color: #808080; font-style: italic;&quot;&gt;// Affiche une erreur&lt;/span&gt;
&lt;span style=&quot;color: #ff0000&quot;&gt;$c&lt;/span&gt; &lt;span style=&quot;color: #66cc66;&quot;&gt;=&lt;/span&gt; &lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;new&lt;/span&gt; Singleton&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#40;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;&amp;#41;&lt;/span&gt;&lt;span style=&quot;color: #66cc66;&quot;&gt;;&lt;/span&gt;
&lt;span style=&quot;color: #000000; font-weight: bold;&quot;&gt;?&amp;gt;&lt;/span&gt;&lt;/pre&gt;


&lt;h3&gt;Conclusion&lt;/h3&gt;

&lt;p&gt;Cet article peut aussi être considéré comme une bonne raison de passer à la version supérieur de php, PHP5. Malheureusement, beaucoup d'hébergeurs tardent à le faire, laissant un PHP4 vieillissant, alors que l'on parle déjà de la version 6!&lt;/p&gt;


&lt;p&gt;C'est d'ailleurs la raison pour laquelle j'insiste si fortement sur les singletons en PHP4. Car s'il est simple de créer de véritable singleton en PHP5, en PHP4 c'est un peu plus compliqué et je pense que vous l'aurez compris en lisant cet article. A propos, le système que j'ai mis au point vous est proposé tel quel et sans aucune garantie. Si vous souhaitez l'utiliser, c'est à vos risques. Toutefois je serais curieux d'avoir vos avis sur ce code, n'hésitez donc pas à le commenter.&lt;/p&gt;</description>
    
    
    
          <comments>http://www.code-web.org/post/2007/11/12/23-un-singleton-en-php#comment-form</comments>
      <wfw:comment>http://www.code-web.org/post/2007/11/12/23-un-singleton-en-php#comment-form</wfw:comment>
      <wfw:commentRss>http://www.code-web.org/feed/rss2/comments/8</wfw:commentRss>
    						<h3>Abonnement aux commentaires</h3>
						<p>
							<a href="http://www.code-web.org/subscribetocomments?post_id=8">
								<!-- # If the subscriber is logged in -->
																<!-- # If the subscriber is not logged in -->
																	S'abonner pour recevoir les commentaires suivants par email															</a>
						</p>
					  </item>
    
</channel>
</rss>