<?php
include_once $_SERVER['DOCUMENT_ROOT'] . '/include/shared-manual.inc';
$TOC = array();
$TOC_DEPRECATED = array();
$PARENTS = array();
include_once dirname(__FILE__) ."/toc/migration74.inc";
$setup = array (
  'home' => 
  array (
    0 => 'index.php',
    1 => 'PHP Manual',
  ),
  'head' => 
  array (
    0 => 'UTF-8',
    1 => 'es',
  ),
  'this' => 
  array (
    0 => 'migration74.new-features.php',
    1 => 'Nuevas caracter&iacute;sticas',
    2 => 'Nuevas caracter&iacute;sticas',
  ),
  'up' => 
  array (
    0 => 'migration74.php',
    1 => 'Migraci&oacute;n de PHP 7.3.x a PHP 7.4.x',
  ),
  'prev' => 
  array (
    0 => 'migration74.php',
    1 => 'Migraci&oacute;n de PHP 7.3.x a PHP 7.4.x',
  ),
  'next' => 
  array (
    0 => 'migration74.new-classes.php',
    1 => 'Nuevas clases e interfaces',
  ),
  'alternatives' => 
  array (
  ),
  'source' => 
  array (
    'lang' => 'es',
    'path' => 'appendices/migration74/new-features.xml',
  ),
  'history' => 
  array (
  ),
);
$setup["toc"] = $TOC;
$setup["toc_deprecated"] = $TOC_DEPRECATED;
$setup["parents"] = $PARENTS;
manual_setup($setup);

contributors($setup);

?>
<div id="migration74.new-features" class="sect1">
 <h2 class="title">Nuevas características</h2>

 <div class="sect2" id="migration74.new-features.core">
  <h3 class="title">Núcleo de PHP</h3>

  <div class="sect3" id="migration74.new-features.core.typed-properties">
   <h4 class="title">Propiedades tipadas</h4>

   <p class="para">
    Las propiedades de las clases ahora soportan la declaración de tipos.
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br /></span><span style="color: #007700">class </span><span style="color: #0000BB">User </span><span style="color: #007700">{<br />    public </span><span style="color: #0000BB">int $id</span><span style="color: #007700">;<br />    public </span><span style="color: #0000BB">string $name</span><span style="color: #007700">;<br />}<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
    El ejemplo anterior asegura que <code class="literal">$user-&gt;id</code> solo puede
    recibir valores de tipo <span class="type"><a href="language.types.integer.php" class="type int">int</a></span> y
    <code class="literal">$user-&gt;name</code> solo puede recibir valores de tipo
    <span class="type"><a href="language.types.string.php" class="type string">string</a></span>.
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.core.arrow-functions">
   <h4 class="title">Funciones flecha</h4>

   <p class="para">
    Las <a href="functions.arrow.php" class="link">funciones flecha</a> proporcionan
    una sintaxis corta para definir funciones que enlazan el ámbito por valor de manera implícita.

    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br />$factor </span><span style="color: #007700">= </span><span style="color: #0000BB">10</span><span style="color: #007700">;<br /></span><span style="color: #0000BB">$nums </span><span style="color: #007700">= </span><span style="color: #0000BB">array_map</span><span style="color: #007700">(fn(</span><span style="color: #0000BB">$n</span><span style="color: #007700">) =&gt; </span><span style="color: #0000BB">$n </span><span style="color: #007700">* </span><span style="color: #0000BB">$factor</span><span style="color: #007700">, [</span><span style="color: #0000BB">1</span><span style="color: #007700">, </span><span style="color: #0000BB">2</span><span style="color: #007700">, </span><span style="color: #0000BB">3</span><span style="color: #007700">, </span><span style="color: #0000BB">4</span><span style="color: #007700">]);<br /></span><span style="color: #FF8000">// $nums = array(10, 20, 30, 40);<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.core.type-variance">
   <h4 class="title">Tipo de retorno covariante y tipo de argumento contravariante limitado</h4>

   <p class="para">
    El siguiente código ahora funcionará:
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br /></span><span style="color: #007700">class </span><span style="color: #0000BB">A </span><span style="color: #007700">{}<br />class </span><span style="color: #0000BB">B </span><span style="color: #007700">extends </span><span style="color: #0000BB">A </span><span style="color: #007700">{}<br /><br />class </span><span style="color: #0000BB">Producer </span><span style="color: #007700">{<br />    public function </span><span style="color: #0000BB">method</span><span style="color: #007700">(): </span><span style="color: #0000BB">A </span><span style="color: #007700">{}<br />}<br />class </span><span style="color: #0000BB">ChildProducer </span><span style="color: #007700">extends </span><span style="color: #0000BB">Producer </span><span style="color: #007700">{<br />    public function </span><span style="color: #0000BB">method</span><span style="color: #007700">(): </span><span style="color: #0000BB">B </span><span style="color: #007700">{}<br />}<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
    El soporte de varianza total solo está disponible cuando se utiliza la carga automática. En un único fichero solo son posibles referencias de tipos no cíclicos, ya que todas las clases deben estar disponibles antes de ser referenciadas.
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br /><br /></span><span style="color: #FF8000">/**<br /> * Estas clases satisfacen los requisitos del LSP, ya que C es un subtipo de A.<br /> * Sin embargo, en el momento en que se declara la clase B, la clase C aún no está disponible<br /> */<br /></span><span style="color: #007700">class </span><span style="color: #0000BB">A<br /></span><span style="color: #007700">{<br />    public function </span><span style="color: #0000BB">method</span><span style="color: #007700">(): </span><span style="color: #0000BB">A </span><span style="color: #007700">{}<br />}<br /><br />class </span><span style="color: #0000BB">B </span><span style="color: #007700">extends </span><span style="color: #0000BB">A<br /></span><span style="color: #007700">{<br />    </span><span style="color: #FF8000">// Error fatal: No se puede verificar la compatibilidad entre B::method():C y<br />    // A::method(): A, ya que la clase C no está disponible<br />    </span><span style="color: #007700">public function </span><span style="color: #0000BB">method</span><span style="color: #007700">(): </span><span style="color: #0000BB">С </span><span style="color: #007700">{}<br />}<br /><br />class </span><span style="color: #0000BB">C </span><span style="color: #007700">extends </span><span style="color: #0000BB">B </span><span style="color: #007700">{}<br /><br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.core.null-coalescing-assignment-operator">
   <h4 class="title">Operador de asignación de fusión Null</h4>

   <p class="para">
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br />$array</span><span style="color: #007700">[</span><span style="color: #DD0000">'key'</span><span style="color: #007700">] ??= </span><span style="color: #0000BB">computeDefault</span><span style="color: #007700">();<br /></span><span style="color: #FF8000">// es aproximadamente equivalente a<br /></span><span style="color: #007700">if (!isset(</span><span style="color: #0000BB">$array</span><span style="color: #007700">[</span><span style="color: #DD0000">'key'</span><span style="color: #007700">])) {<br />    </span><span style="color: #0000BB">$array</span><span style="color: #007700">[</span><span style="color: #DD0000">'key'</span><span style="color: #007700">] = </span><span style="color: #0000BB">computeDefault</span><span style="color: #007700">();<br />}<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.core.unpack-inside-array">
   <h4 class="title">Desempaquetado en los arrays</h4>

   <p class="para">
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br />$parts </span><span style="color: #007700">= [</span><span style="color: #DD0000">'apple'</span><span style="color: #007700">, </span><span style="color: #DD0000">'pear'</span><span style="color: #007700">];<br /></span><span style="color: #0000BB">$fruits </span><span style="color: #007700">= [</span><span style="color: #DD0000">'banana'</span><span style="color: #007700">, </span><span style="color: #DD0000">'orange'</span><span style="color: #007700">, ...</span><span style="color: #0000BB">$parts</span><span style="color: #007700">, </span><span style="color: #DD0000">'watermelon'</span><span style="color: #007700">];<br /></span><span style="color: #FF8000">// ['banana', 'orange', 'apple', 'pear', 'watermelon'];<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.core.numeric-literal-separator">
   <h4 class="title">Separador numérico literal</h4>

   <p class="para">
    Los números literales pueden contener un carácter de subrayado entre
    los dígitos.
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br />6.674_083e-11</span><span style="color: #007700">; </span><span style="color: #FF8000">// float<br /></span><span style="color: #0000BB">299_792_458</span><span style="color: #007700">;   </span><span style="color: #FF8000">// decimal<br /></span><span style="color: #0000BB">0xCAFE_F00D</span><span style="color: #007700">;   </span><span style="color: #FF8000">// hexadecimal<br /></span><span style="color: #0000BB">0b0101_1111</span><span style="color: #007700">;   </span><span style="color: #FF8000">// binario<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.core.weakreference">
   <h4 class="title">Referencias débiles</h4>

   <p class="para">
    Las <a href="class.weakreference.php" class="link">referencias débiles</a> permiten al desarrollador retener una referencia
    a un objeto que no impide que el objeto sea destruido.
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.core.tostring-exceptions">
   <h4 class="title">Permitir Excepciones desde __toString()</h4>

   <p class="para">
    Lanzar excepciones desde <a href="language.oop5.magic.php#object.tostring" class="link">__toString()</a>
    ahora está permitido. Anteriormente, esto resultaba en un error fatal.
    Los errores fatales recuperables en las conversiones de <span class="type"><a href="language.types.string.php" class="type string">string</a></span> han sido
    convertidos en excepciones <span class="classname"><a href="class.error.php" class="classname">Error</a></span>.
   </p>
  </div>

 </div>

 <div class="sect2" id="migration74.new-features.curl">
  <h3 class="title">CURL</h3>

  <p class="para">
   <span class="classname"><a href="class.curlfile.php" class="classname">CURLFile</a></span> ahora soporta las envolturas de flujo
   además de los nombres de ficheros brutos, si la extensión ha sido compilada con libcurl
   &gt;= 7.56.0.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.filter">
  <h3 class="title">Filtro</h3>

  <p class="para">
   El filtro <strong><code><a href="filter.constants.php#constant.filter-validate-float">FILTER_VALIDATE_FLOAT</a></code></strong> ahora soporta las
   opciones <code class="literal">min_range</code> y <code class="literal">max_range</code>,
   con la misma sémantica que <strong><code><a href="filter.constants.php#constant.filter-validate-int">FILTER_VALIDATE_INT</a></code></strong>.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.ffi">
  <h3 class="title">FFI</h3>

  <p class="para">
   FFI es una nueva extensión, que proporciona una manera sencilla de llamar
   a las funciones nativas, acceso nativo a las variables, y la creación/acceso a
   estructuras de datos definidas en bibliotecas C.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.gd">
  <h3 class="title">GD</h3>

  <p class="para">
   Se ha añadido el filtro de imagen <strong><code><a href="image.constants.php#constant.img-filter-scatter">IMG_FILTER_SCATTER</a></code></strong>
   para aplicar un filtro de dispersión a las imágenes.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.hash">
  <h3 class="title">Hash</h3>

  <p class="para">
   Se ha añadido el hash <code class="literal">crc32c</code> utilizando el polinomio de Castagnoli.
   Esta variante de CRC32 es utilizada por sistemas de almacenamiento, tales como
   iSCSI, SCTP, Btrfs y ext4.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.mbstring">
  <h3 class="title">Cadenas multioctetos</h3>

  <p class="para">
   Se ha añadido la función <span class="function"><a href="function.mb-str-split.php" class="function">mb_str_split()</a></span>, que proporciona la misma
   funcionalidad que <span class="function"><a href="function.str-split.php" class="function">str_split()</a></span>, pero opera sobre puntos de código en lugar de octetos.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.opcache">
  <h3 class="title">OPcache</h3>

  <p class="para">
   <a href="opcache.preloading.php" class="link">El soporte para la precarga de código</a> ha sido añadido.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.pcre">
  <h3 class="title">Expresiones Regulares (Compatible Perl)</h3>

  <p class="para">
   Las funciones <span class="function"><a href="function.preg-replace-callback.php" class="function">preg_replace_callback()</a></span> y
   <span class="function"><a href="function.preg-replace-callback-array.php" class="function">preg_replace_callback_array()</a></span> ahora aceptan un
   argumento <code class="parameter">flags</code> adicional, con soporte para los
   flags <strong><code><a href="pcre.constants.php#constant.preg-offset-capture">PREG_OFFSET_CAPTURE</a></code></strong> y
   <strong><code><a href="pcre.constants.php#constant.preg-unmatched-as-null">PREG_UNMATCHED_AS_NULL</a></code></strong>.
   Esto influye en el formato del <span class="type"><a href="language.types.array.php" class="type array">array</a></span> de coincidencias pasado a la función de retrollamada.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.pdo">
  <h3 class="title">PDO</h3>

  <p class="para">
   El nombre de usuario y la contraseña ahora pueden ser especificados como
   parte del DSN PDO para los controladores mysql, mssql, sybase, dblib, firebird
   y oci. Anteriormente, esto solo era soportado para el controlador pgsql.
   Si un nombre de usuario/contraseña es definido tanto en el
   constructor como en el DSN, el constructor tiene precedencia.
  </p>
  <p class="para">
   Ahora es posible escapar los signos de interrogación en las consultas SQL para evitar que sean interpretados como parámetro ficticio.
   Escribir <code class="literal">??</code> permite enviar un solo signo de interrogación
   a la base de datos y, por ejemplo, utilizar el operador PostgreSQL JSON
   para saber si una clave existe (<code class="literal">?</code>).
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.pdo_oci">
  <h3 class="title">PDO_OCI</h3>

  <p class="para">
   <span class="methodname"><a href="pdostatement.getcolumnmeta.php" class="methodname">PDOStatement::getColumnMeta()</a></span> ahora está disponible.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.pdo_sqlite">
  <h3 class="title">PDO_SQLite</h3>

  <p class="para">
   <code class="literal">PDOStatement::getAttribute(PDO::SQLITE_ATTR_READONLY_STATEMENT)</code>
   permite verificar si la declaración es de solo lectura, es decir, si no
   modifica la base de datos.
  </p>
  <p class="para">
   <code class="literal">PDO::setAttribute(PDO::SQLITE_ATTR_EXTENDED_RESULT_CODES, true)</code>
   activa el uso de códigos de resultados extendidos en
   <span class="function"><a href="pdo.errorinfo.php" class="function">PDO::errorInfo()</a></span> y
   <span class="function"><a href="pdostatement.errorinfo.php" class="function">PDOStatement::errorInfo()</a></span>.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.sqlite3">
  <h3 class="title">SQLite3</h3>

  <p class="para">
   Se ha añadido <span class="methodname"><strong>SQLite3::lastExtendedErrorCode()</strong></span>
   para recuperar el último código extendido del resultado.
  </p>
  <p class="para">
   Se ha añadido <code class="literal">SQLite3::enableExtendedResultCodes($enable = true)</code>,
   que hará que <span class="methodname"><a href="sqlite3.lasterrorcode.php" class="methodname">SQLite3::lastErrorCode()</a></span> devuelva códigos de resultados extendidos.
  </p>
 </div>

 <div class="sect2" id="migration74.new-features.standard">
  <h3 class="title">Estándar</h3>

  <div class="sect3" id="migration74.new-features.standard.strip-tags">
   <h4 class="title">strip_tags() con un array de nombres de tag</h4>
   <p class="para">
    <span class="function"><a href="function.strip-tags.php" class="function">strip_tags()</a></span> ahora acepta un <span class="type"><a href="language.types.array.php" class="type array">array</a></span> de tags
    permitidos: en lugar de
    <code class="literal">strip_tags($str, &#039;&lt;a&gt;&lt;p&gt;&#039;)</code> ahora es posible escribir <code class="literal">strip_tags($str, [&#039;a&#039;, &#039;p&#039;])</code>.
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.standard.magic-serialize">
   <h4 class="title">Serialización personalizada de objetos</h4>
   <p class="para">
    Se ha añadido un nuevo mecanismo de serialización personalizada de objetos,
    que utiliza dos nuevas métodos mágicos:
    <code class="literal">__serialize</code> y <code class="literal">__unserialize</code>.
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br /></span><span style="color: #FF8000">// Devuelve un array que contiene todo el estado necesario del objeto.<br /></span><span style="color: #007700">public function </span><span style="color: #0000BB">__serialize</span><span style="color: #007700">(): array<br />{<br />}<br /><br /></span><span style="color: #FF8000">// Restaura el estado de un objeto desde el array de datos proporcionado.<br /></span><span style="color: #007700">public function </span><span style="color: #0000BB">__unserialize</span><span style="color: #007700">(array </span><span style="color: #0000BB">$data</span><span style="color: #007700">): </span><span style="color: #0000BB">void<br /></span><span style="color: #007700">{<br />}<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
    El nuevo mecanismo de serialización sucederá a la interfaz
    <span class="interfacename"><a href="class.serializable.php" class="interfacename">Serializable</a></span>, que será obsoleto en el futuro.
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.standard.array-merge-no-args">
   <h4 class="title">Las funciones array merge sin argumentos</h4>
   <p class="para">
    <span class="function"><a href="function.array-merge.php" class="function">array_merge()</a></span> y <span class="function"><a href="function.array-merge-recursive.php" class="function">array_merge_recursive()</a></span>
    ahora pueden ser llamadas sin argumentos, en cuyo caso
    devolverán un <span class="type"><a href="language.types.array.php" class="type array">array</a></span> vacío. Esto es útil en conjunción con el operador
    de descomposición, por ejemplo <code class="literal">array_merge(...$arrays)</code>.
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.standard.proc-open">
   <h4 class="title">La función <span class="function"><a href="function.proc-open.php" class="function">proc_open()</a></span></h4>
   <p class="para">
    <span class="function"><a href="function.proc-open.php" class="function">proc_open()</a></span> ahora acepta un <span class="type"><a href="language.types.array.php" class="type array">array</a></span> en lugar de una
    <span class="type"><a href="language.types.string.php" class="type string">string</a></span> para la comanda. En este caso, el proceso se abre directamente
    (sin pasar a través de un shell) y PHP se encargará de escapar los argumentos
    cuando sea necesario.
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br />proc_open</span><span style="color: #007700">([</span><span style="color: #DD0000">'php'</span><span style="color: #007700">, </span><span style="color: #DD0000">'-r'</span><span style="color: #007700">, </span><span style="color: #DD0000">'echo "Hello World\n";'</span><span style="color: #007700">], </span><span style="color: #0000BB">$descriptors</span><span style="color: #007700">, </span><span style="color: #0000BB">$pipes</span><span style="color: #007700">);<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
   </p>
   <p class="para">
    <span class="function"><a href="function.proc-open.php" class="function">proc_open()</a></span> ahora soporta los descriptores
    <code class="literal">redirect</code> y <code class="literal">null</code>.
    <div class="informalexample">
     <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br /></span><span style="color: #FF8000">// Como 2&gt;&amp;1 en el shell<br /></span><span style="color: #0000BB">proc_open</span><span style="color: #007700">(</span><span style="color: #0000BB">$cmd</span><span style="color: #007700">, [</span><span style="color: #0000BB">1 </span><span style="color: #007700">=&gt; [</span><span style="color: #DD0000">'pipe'</span><span style="color: #007700">, </span><span style="color: #DD0000">'w'</span><span style="color: #007700">], </span><span style="color: #0000BB">2 </span><span style="color: #007700">=&gt; [</span><span style="color: #DD0000">'redirect'</span><span style="color: #007700">, </span><span style="color: #0000BB">1</span><span style="color: #007700">]], </span><span style="color: #0000BB">$pipes</span><span style="color: #007700">);<br /></span><span style="color: #FF8000">// Como 2&gt;/dev/null o 2&gt;nul en el shell<br /></span><span style="color: #0000BB">proc_open</span><span style="color: #007700">(</span><span style="color: #0000BB">$cmd</span><span style="color: #007700">, [</span><span style="color: #0000BB">1 </span><span style="color: #007700">=&gt; [</span><span style="color: #DD0000">'pipe'</span><span style="color: #007700">, </span><span style="color: #DD0000">'w'</span><span style="color: #007700">], </span><span style="color: #0000BB">2 </span><span style="color: #007700">=&gt; [</span><span style="color: #DD0000">'null'</span><span style="color: #007700">]], </span><span style="color: #0000BB">$pipes</span><span style="color: #007700">);<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
     </div>

    </div>
   </p>
  </div>

  <div class="sect3" id="migration74.new-features.standard.sodium-argon-hash">
   <h4 class="title">argon2i(d) sin libargon</h4>
   <p class="para">
    <span class="function"><a href="function.password-hash.php" class="function">password_hash()</a></span> ahora tiene las implementaciones de
    argon2i y argon2id de la extensión sodium cuando PHP es compilado sin libargon.
   </p>
  </div>

 </div>

</div><?php manual_footer($setup); ?>