GoGPT Best VPN GoSearch

icono de página de OnWorks

perlref - Online en la nube

Ejecute perlref en el proveedor de alojamiento gratuito de OnWorks sobre Ubuntu Online, Fedora Online, emulador en línea de Windows o emulador en línea de MAC OS

Este es el comando perlref que se puede ejecutar en el proveedor de alojamiento gratuito de OnWorks utilizando una de nuestras múltiples estaciones de trabajo en línea gratuitas, como Ubuntu Online, Fedora Online, emulador en línea de Windows o emulador en línea de MAC OS.

PROGRAMA:

NOMBRE


perlref - Referencias de Perl y estructuras de datos anidadas

NOTA


Esta es la documentación completa sobre todos los aspectos de las referencias. Para un tutorial más corto
introducción a las funciones esenciales, consulte perlreftut.

DESCRIPCIÓN


Antes del lanzamiento 5 de Perl era difícil representar estructuras de datos complejas, porque
todas las referencias tenían que ser simbólicas, e incluso entonces era difícil hacer referencia a una variable
en lugar de una entrada de tabla de símbolos. Perl ahora no solo facilita el uso de símbolos
referencias a variables, pero también le permite tener referencias "duras" a cualquier dato o
código. Cualquier escalar puede contener una referencia sólida. Debido a que las matrices y los hash contienen escalares,
ahora puede construir fácilmente matrices de matrices, matrices de hashes, hashes de matrices, matrices de
hashes de funciones, etc.

Las referencias duras son inteligentes: realizan un seguimiento de los recuentos de referencias automáticamente
liberando la cosa referida cuando su recuento de referencia llega a cero. (Recuentos de referencia
para los valores en estructuras de datos autorreferenciales o cíclicas no pueden ir a cero sin un
un poco de ayuda; consulte "Referencias circulares" para obtener una explicación detallada).
para ser un objeto, el objeto se destruye. Consulte perlobj para obtener más información sobre los objetos. (En un
sentido, todo en Perl es un objeto, pero normalmente reservamos la palabra para referencias a
objetos que han sido "bendecidos" oficialmente en un paquete de clase).

Las referencias simbólicas son nombres de variables u otros objetos, como un enlace simbólico en un
El sistema de archivos Unix contiene simplemente el nombre de un archivo. La notación * glob es una especie de
referencia simbólica. (Las referencias simbólicas a veces se denominan "referencias suaves", pero
por favor no los llames así; las referencias son lo suficientemente confusas sin sinónimos inútiles).

Por el contrario, las referencias físicas son más como enlaces físicos en un sistema de archivos Unix: se utilizan
para acceder a un objeto subyacente sin preocuparse por su (otro) nombre. Cuando el
La palabra "referencia" se usa sin un adjetivo, como en el siguiente párrafo, es
generalmente hablando de una referencia dura.

Las referencias son fáciles de usar en Perl. Solo hay un principio fundamental: en general,
Perl no hace referencias ni desreferenciaciones implícitas. Cuando un escalar tiene una referencia,
siempre se comporta como un escalar simple. No comienza mágicamente a ser una matriz o hash
o subrutina; tienes que decirle explícitamente que lo haga, eliminándolo.

Dicho esto, tenga en cuenta que la versión 5.14 de Perl introduce una excepción a la regla, para
conveniencia sintáctica. El comportamiento de la función de contenedor de hash y matriz experimental permite
matrices y referencias hash para ser manejadas por Perl como si hubieran sido explícitamente
desreferenciado sintácticamente. Consulte "Mejoras sintácticas" en perl5140delta y perlfunc.
para obtener más detalles.

Realizar Referencias
Las referencias se pueden crear de varias formas.

1. Utilizando el operador de barra invertida en una variable, subrutina o valor. (Esto funciona mucho
como el operador & (dirección de) en C.) Esto normalmente crea una alternativa, referencia a un
variable, porque ya hay una referencia a la variable en la tabla de símbolos.
Pero la referencia de la tabla de símbolos puede desaparecer y todavía tendrá la referencia que
la barra invertida volvió. Aquí hay unos ejemplos:

$ scalarref = \ $ foo;
$ arrayref = \ @ARGV;
$ hashref = \% ENV;
$ coderef = \ & handler;
$ globref = \ * foo;

No es posible crear una referencia verdadera a un identificador de E / S (identificador de archivo o identificador de directorio)
usando el operador de barra invertida. Lo máximo que puede obtener es una referencia a un typeglob,
que es en realidad una entrada completa de la tabla de símbolos. Pero mira la explicación del
* foo {COSA} sintaxis a continuación. Sin embargo, todavía puede utilizar type globs y globrefs como
aunque eran manijas de IO.

2. Se puede crear una referencia a una matriz anónima utilizando corchetes:

$ arrayref = [1, 2, ['a', 'b', 'c']];

Aquí hemos creado una referencia a una matriz anónima de tres elementos cuyo final
elemento es en sí mismo una referencia a otra matriz anónima de tres elementos. (Los
La sintaxis multidimensional que se describe más adelante se puede utilizar para acceder a esto. Por ejemplo,
después de lo anterior, "$ arrayref -> [2] [1]" tendría el valor "b".)

Tomar una referencia a una lista enumerada no es lo mismo que usar cuadrado
corchetes; en cambio, es lo mismo que crear una lista de referencias.

@list = (\ $ a, \ @b, \% c);
@list = \ ($ a, @b,% c); # ¡la misma cosa!

Como caso especial, "\ (@ foo)" devuelve una lista de referencias al contenido de @foo, no
una referencia al propio @foo. Lo mismo ocurre con% foo, excepto que las referencias clave son para
copias (dado que las claves son solo cadenas en lugar de escalares completos).

3. Se puede crear una referencia a un hash anónimo utilizando llaves:

$ hashref = {
'Adam' => 'Eva',
'Clyde' => 'Bonnie',
};

Los compositores de matrices y hash anónimos como estos se pueden mezclar libremente para producir como
complica una estructura como quieras. La sintaxis multidimensional que se describe a continuación
también funciona para estos. Los valores anteriores son literales, pero variables y expresiones
funcionaría igual de bien, porque los operadores de asignación en Perl (incluso dentro local() or
mi()) son declaraciones ejecutables, no declaraciones en tiempo de compilación.

Debido a que las llaves (llaves) se utilizan para varias otras cosas, incluidos BLOQUES,
Es posible que ocasionalmente tenga que eliminar la ambigüedad de los frenos al comienzo de una declaración al
poner un "+" o un "retorno" al frente para que Perl se dé cuenta de que la llave de apertura no
comenzando un BLOQUE. La economía y el valor mnemónico de usar curlies se considera que vale la pena.
esta molestia adicional ocasional.

Por ejemplo, si desea que una función cree un nuevo hash y le devuelva una referencia,
tienes estas opciones:

sub hashem {{@_}} # silenciosamente mal
sub hashem {+ {@_}} # ok
sub hashem {return {@_}} # ok

Por otro lado, si desea el otro significado, puede hacer esto:

sub showem {{@_}} # ambiguous (actualmente ok,
# pero puede cambiar)
sub showem {{; @_ } } # OK
sub showem {{return @_}} # ok

El "+ {" y "{;" iniciales siempre sirven para eliminar la ambigüedad de la expresión para que signifique
la referencia HASH, o el BLOQUE.

4. Se puede crear una referencia a una subrutina anónima usando "sub" sin un
subnombre:

$ coderef = sub {imprimir "¡Boink! \ n"};

Tenga en cuenta el punto y coma. Excepto por el código interno que no se ejecuta inmediatamente, un "sub
{} "no es tanto una declaración como un operador, como" do {} "o" eval {} ".
(Sin embargo, no importa cuántas veces ejecute esa línea en particular (a menos que esté en
an "eval (" ... ")"), $ coderef todavía tendrá una referencia al mismo anónimo
subrutina.)

Las subrutinas anónimas actúan como cierres con respecto a mi() variables, es decir,
variables léxicamente visibles dentro del ámbito actual. El cierre es una noción fuera del
Lisp mundo que dice si define una función anónima en un léxico particular
contexto, pretende ejecutarse en ese contexto incluso cuando se llama fuera del contexto.

En términos humanos, es una forma divertida de pasar argumentos a una subrutina cuando define
así como cuando lo llames. Es útil para configurar pequeños fragmentos de código para ejecutar
más tarde, como devoluciones de llamada. Incluso puede hacer cosas orientadas a objetos con él, aunque Perl
ya proporciona un mecanismo diferente para hacer eso - ver perlobj.

También puede pensar en el cierre como una forma de escribir una plantilla de subrutina sin usar
eval (). Aquí hay un pequeño ejemplo de cómo funcionan los cierres:

sub letra nueva {
my $ x = turno;
return sub {my $ y = shift; imprimir "$ x, $ y! \ n"; };
}
$ h = newprint ("Hola");
$ g = newprint ("Saludos");

# El tiempo pasa...

& $ h ("mundo");
& $ g ("terrícolas");

Esto imprime

¡Hola, mundo!
¡Saludos, terrícolas!

Tenga en cuenta en particular que $ x sigue refiriéndose al valor pasado a newprint ()
a pesar de "my $ x" ha salido del alcance en el momento en que se ejecuta la subrutina anónima.
De eso se trata un cierre.

Esto se aplica solo a las variables léxicas, por cierto. Las variables dinámicas continúan
trabajen como siempre han trabajado. El cierre no es algo que la mayoría de los programadores de Perl
necesitan preocuparse para empezar.

5. Las referencias a menudo son devueltas por subrutinas especiales llamadas constructores. Perl
Los objetos son solo referencias a un tipo especial de objeto que sabe qué
paquete con el que está asociado. Los constructores son solo subrutinas especiales que saben cómo
para crear esa asociación. Lo hacen comenzando con una referencia ordinaria, y
sigue siendo una referencia ordinaria incluso cuando también es un objeto. Los constructores son
a menudo denominado "nuevo ()". usted can llamarlos indirectamente:

$ objref = new Doggie (Tail => 'short', Ears => 'long');

Pero eso puede producir una sintaxis ambigua en ciertos casos, por lo que a menudo es mejor usar
el enfoque de invocación de método directo:

$ objref = Perrito-> nuevo (Cola => 'corto', Orejas => 'largo');

use Term :: Cap;
$ terminal = Término :: Cap-> Tgetent ({OSPEED => 9600});

usar Tk;
$ main = MainWindow-> new ();
$ menubar = $ main-> Frame (-relief => "elevado",
-borderwidth => 2)

6. Las referencias del tipo apropiado pueden surgir si las elimina.
en un contexto que asume que existen. Porque no hemos hablado de desreferenciar
sin embargo, todavía no podemos mostrarle ningún ejemplo.

7. Se puede crear una referencia usando una sintaxis especial, conocida cariñosamente como el
* foo {COSA} sintaxis. * foo {COSA} devuelve una referencia al espacio COSA en * foo (que
es la entrada de la tabla de símbolos que contiene todo lo que se conoce como foo).

$ scalarref = * foo {ESCALAR};
$ arrayref = * ARGV {ARRAY};
$ hashref = * ENV {HASH};
$ coderef = * manejador {CÓDIGO};
$ ioref = * STDIN {IO};
$ globref = * foo {GLOB};
$ formatref = * foo {FORMAT};
$ globname = * foo {NOMBRE}; # "foo"
$ pkgname = * foo {PAQUETE}; # "principal"

La mayoría de ellos se explican por sí mismos, pero * foo {IO} merece una atención especial. Eso
devuelve el identificador IO, utilizado para identificadores de archivos ("abrir" en perlfunc), sockets ("socket"
en perlfunc y "socketpair" en perlfunc), y los identificadores de directorio ("opendir" en
perlfunc). Para compatibilidad con versiones anteriores de Perl, * foo {FILEHANDLE} es un
sinónimo de * foo {IO}, aunque está obsoleto a partir de 5.8.0. Si las advertencias de depreciación
están en vigor, advertirá de su uso.

* foo {COSA} devuelve undef si esa COSA en particular no se ha utilizado todavía, excepto en el
caso de escalares. * foo {ESCALAR} devuelve una referencia a un escalar anónimo si $ foo
aún no se ha utilizado. Esto podría cambiar en una versión futura.

* foo {NAME} y * foo {PAQUETE} son la excepción, ya que devuelven cadenas, en lugar de
que las referencias. Estos devuelven el paquete y el nombre del typeglob en sí, en lugar de
que uno que le ha sido asignado. Entonces, después de "* foo = * Foo :: bar", * foo se convertirá en
"* Foo :: bar" cuando se usa como una cadena, pero * foo {PAQUETE} y * foo {NOMBRE} continuarán
producen "main" y "foo", respectivamente.

* foo {IO} es una alternativa al mecanismo * HANDLE dado en "Typeglobs y
Filehandles "en perldata para pasar identificadores de archivo dentro o fuera de subrutinas, o
almacenar en estructuras de datos más grandes. Su desventaja es que no creará un nuevo
filehandle para usted. Su ventaja es que tiene menos riesgo de golpear más que
desea con una asignación de typeglob. (Todavía combina archivos y directorios
maneja, sin embargo.) Sin embargo, si asigna el valor entrante a un escalar en lugar de un
typeglob como lo hacemos en los ejemplos a continuación, no hay riesgo de que eso suceda.

farfullar (* STDOUT); # pasar todo el globo
balbuceo (* STDOUT {IO}); # pasar los identificadores de archivos y directorios

sub balbuceo {
my $ fh = turno;
print $ fh "her um bueno a hmmm \ n";
}

$ rec = get_rec (* STDIN); # pasar todo el globo
$ rec = get_rec (* STDIN {IO}); # pasar los identificadores de archivos y directorios

sub get_rec {
my $ fh = turno;
return escalar <$ fh>;
}

Usando Referencias
Eso es todo por crear referencias. A estas alturas probablemente te mueras por saber cómo usar
referencias para volver a sus datos perdidos hace mucho tiempo. Existen varios métodos básicos.

1. En cualquier lugar en el que coloque un identificador (o una cadena de identificadores) como parte de una variable o
nombre de la subrutina, puede reemplazar el identificador con una variable escalar simple
que contiene una referencia del tipo correcto:

$ barra = $$ scalarref;
push (@ $ arrayref, $ nombre de archivo);
$$ arrayref [0] = "Enero";
$$ hashref {"CLAVE"} = "VALOR";
& $ coderef (1,2,3);
print $ globref "salida \ n";

Es importante comprender que somos específicamente No desreferenciar $ arrayref [0]
o $ hashref {"KEY"} allí. La desreferencia de la variable escalar ocurre antes it
realiza búsquedas clave. Cualquier cosa más complicada que una simple variable escalar debe
utilice los métodos 2 o 3 a continuación. Sin embargo, un "escalar simple" incluye un identificador que
en sí mismo utiliza el método 1 de forma recursiva. Por lo tanto, lo siguiente imprime "hola".

$ refrefref = \\\ "hola";
imprimir $$$$ refrefref;

2. En cualquier lugar en el que coloque un identificador (o una cadena de identificadores) como parte de una variable o
nombre de la subrutina, puede reemplazar el identificador con un BLOQUE que devuelve una referencia de
el tipo correcto. En otras palabras, los ejemplos anteriores podrían escribirse así:

$ barra = $ {$ scalarref};
push (@ {$ arrayref}, $ nombre de archivo);
$ {$ arrayref} [0] = "enero";
$ {$ hashref} {"CLAVE"} = "VALOR";
& {$ coderef} (1,2,3);
$ globref-> print ("salida \ n"); # iff IO :: Handle está cargado

Es cierto que es un poco tonto usar los rizos en este caso, pero el BLOQUE puede
contener cualquier expresión arbitraria, en particular, expresiones subindicadas:

& {$ despacho {$ índice}} (1,2,3); # llamar a la rutina correcta

Debido a que se pueden omitir los curlies para el caso simple de $$ x, la gente a menudo
comete el error de ver los símbolos de desreferenciación como operadores adecuados, y se pregunta
sobre su precedencia. Sin embargo, si lo fueran, podría utilizar paréntesis en lugar de
tirantes. Ese no es el caso. Considere la diferencia a continuación; caso 0 es una abreviatura
versión del caso 1, No caso 2:

$$ hashref {"CLAVE"} = "VALOR"; # CASO 0
$ {$ hashref} {"CLAVE"} = "VALOR"; # CASO 1
$ {$ hashref {"CLAVE"}} = "VALOR"; # CASO 2
$ {$ hashref -> {"CLAVE"}} = "VALOR"; # CASO 3

El caso 2 también es engañoso porque está accediendo a una variable llamada% hashref, no
desreferenciar a través de $ hashref al hash al que presumiblemente hace referencia. Eso sería
caso 3.

3. Las llamadas a subrutinas y las búsquedas de elementos individuales de la matriz surgen con la suficiente frecuencia como para
se vuelve engorroso usar el método 2. Como forma de azúcar sintáctico, los ejemplos de
el método 2 puede escribirse:

$ arrayref -> [0] = "enero"; # Elemento de matriz
$ hashref -> {"CLAVE"} = "VALOR"; # Elemento hash
$ coderef -> (1,2,3); # Llamada a subrutina

El lado izquierdo de la flecha puede ser cualquier expresión que devuelva una referencia, incluida una
desreferencia previa. Tenga en cuenta que $ array [$ x] es No lo mismo que "$ matriz -> [$ x]"
aquí:

$ matriz [$ x] -> {"foo"} -> [0] = "enero";

Este es uno de los casos que mencionamos anteriormente en el que las referencias podrían surgir
existencia cuando se encuentra en un contexto de valor l. Antes de esta declaración, $ array [$ x] puede haber sido
indefinido. Si es así, se define automáticamente con una referencia hash para que podamos
busca "{" foo "}" en él. Del mismo modo, "$ array [$ x] -> {" foo "}" obtendrá automáticamente
definido con una referencia de matriz para que podamos buscar "[0]" en ella. Este proceso es
, que son autovivificación.

Una cosa mas aqui. La flecha es opcional entre subíndices entre corchetes, para que pueda
encoger lo anterior a

$ matriz [$ x] {"foo"} [0] = "enero";

Lo cual, en el caso degenerado de usar solo matrices ordinarias, le da
matrices multidimensionales como las de C:

$ puntuación [$ x] [$ y] [$ z] + = 42;

Bueno, de acuerdo, no del todo como las matrices de C, en realidad. C no sabe cómo hacer crecer su
matrices bajo demanda. Perl lo hace.

4. Si una referencia es una referencia a un objeto, es probable que existan métodos
para acceder a las cosas a las que se hace referencia, y probablemente debería ceñirse a esos métodos
a menos que esté en el paquete de clase que define los métodos del objeto. En otras palabras,
Sea amable y no viole la encapsulación del objeto sin una muy buena razón.
Perl no impone la encapsulación. No somos totalitarios aquí. Nosotros esperamos
aunque algo de cortesía básica.

El uso de una cadena o un número como referencia produce una referencia simbólica, como se explicó anteriormente.
El uso de una referencia como número produce un entero que representa su ubicación de almacenamiento en
memoria. Lo único útil que se puede hacer con esto es comparar dos referencias
numéricamente para ver si se refieren a la misma ubicación.

if ($ ref1 == $ ref2) {# comparación numérica barata de referencias
print "las referencias 1 y 2 se refieren a lo mismo \ n";
}

El uso de una referencia como cadena produce tanto el tipo de su referente, incluido cualquier paquete
bendición como se describe en perlobj, así como la dirección numérica expresada en hexadecimal. los
árbitro() El operador devuelve solo el tipo de cosa a la que apunta la referencia, sin el
Dirección. Consulte "ref" en perlfunc para obtener detalles y ejemplos de su uso.

La planta de bendecir() El operador puede usarse para asociar el objeto al que un punto de referencia con un
paquete que funciona como una clase de objeto. Ver perlobj.

Un typeglob puede desreferenciarse de la misma manera que una referencia, porque la desreferencia
la sintaxis siempre indica el tipo de referencia deseada. Entonces, "$ {* foo}" y "$ {\ $ foo}" ambos
indican la misma variable escalar.

Aquí hay un truco para interpolar una llamada de subrutina en una cadena:

print "Mi sub devolvió @ {[mysub (1,2,3)]} esa vez. \ n";

La forma en que funciona es que cuando se ve "@ {...}" en la cadena entre comillas dobles, es
evaluado como un bloque. El bloque crea una referencia a una matriz anónima que contiene el
resultados de la llamada a "mysub (1,2,3)". Entonces, todo el bloque devuelve una referencia a un
array, que luego es desreferenciado por "@ {...}" y pegado en la cadena entre comillas dobles.
Esta artimaña también es útil para expresiones arbitrarias:

imprimir "Eso produce @ {[$ n + 5]} widgets \ n";

De manera similar, una expresión que devuelve una referencia a un escalar se puede desreferenciar mediante
PS Por lo tanto, la expresión anterior se puede escribir como:

print "Eso produce $ {\ ($ n + 5)} widgets \ n";

Circular Referencias
Es posible crear una "referencia circular" en Perl, lo que puede provocar pérdidas de memoria. A
La referencia circular ocurre cuando dos referencias contienen una referencia entre sí, como
modo:

my $ foo = {};
my $ bar = {foo => $ foo};
$ foo -> {barra} = $ barra;

También puede crear una referencia circular con una sola variable:

my $ foo;
$ foo = \ $ foo;

En este caso, el recuento de referencias para las variables nunca llegará a 0 y las referencias
nunca será recolectado como basura. Esto puede provocar pérdidas de memoria.

Debido a que los objetos en Perl se implementan como referencias, es posible tener circulares
referencias con objetos también. Imagine una clase TreeNode donde cada nodo hace referencia a su
nodos padre e hijo. Cualquier nodo con un padre será parte de una referencia circular.

Puede romper referencias circulares creando una "referencia débil". Una referencia débil hace
no incrementar el recuento de referencia para una variable, lo que significa que el objeto puede salir
de alcance y ser destruido. Puede debilitar una referencia con la función "debilitar" exportada
por el módulo Scalar :: Util.

Así es como podemos hacer que el primer ejemplo sea más seguro:

use Scalar :: Util 'debilitar';

my $ foo = {};
my $ bar = {foo => $ foo};
$ foo -> {barra} = $ barra;

debilitar $ foo -> {bar};

La referencia de $ foo a $ bar se ha debilitado. Cuando la variable $ bar sale de
alcance, será recolectado como basura. La próxima vez que observe el valor de la
Tecla "$ foo -> {bar}", será "indef".

Esta acción a distancia puede resultar confusa, por lo que debe tener cuidado con el uso de
debilitar. Debe debilitar la referencia en la variable que saldrá del alcance first.
De esa forma, la variable de mayor duración contendrá la referencia esperada hasta que se apague.
de alcance.

Simbólico referencias
Dijimos que las referencias surgen como necesarias si no están definidas, pero
no dijo qué sucede si un valor utilizado como referencia ya está definido, pero no es a
referencia dura. Si lo usa como referencia, se tratará como una referencia simbólica.
Es decir, el valor del escalar se toma como el nombre de una variable, en lugar de una
enlace directo a un valor (posiblemente) anónimo.

La gente suele esperar que funcione así. Así es.

$ nombre = "foo";
$$ nombre = 1; # Conjuntos $ foo
$ {$ nombre} = 2; # Conjuntos $ foo
$ {$ nombre x 2} = 3; # Conjuntos $ foofoo
$ nombre -> [0] = 4; # Conjuntos $ foo [0]
@ $ nombre = (); # Borra @foo
& $ nombre (); # Llamadas & foo ()
$ paquete = "ESO";
$ {"$ {paquete} :: $ nombre"} = 5; # Establece $ THAT :: foo sin eval

Esto es poderoso y un poco peligroso, ya que es posible tener la intención (con el máximo
sinceridad) para usar una referencia dura, y accidentalmente usar una referencia simbólica en su lugar. Para
protegerte contra eso, puedes decir

use 'refs' estrictos;

y luego solo se permitirán referencias duras para el resto del bloque adjunto. Un
bloque interno puede contrarrestar eso con

no hay "referencias" estrictas;

Solo las variables de paquete (globales, incluso si están localizadas) son visibles para referencias simbólicas.
Variables léxicas (declaradas con mi()) no están en una tabla de símbolos y, por lo tanto, son invisibles para
este mecanismo. Por ejemplo:

valor $ local = 10;
$ ref = "valor";
{
mi $ valor = 20;
imprimir $$ ref;
}

Esto seguirá imprimiendo 10, no 20. Recuerde que local() afecta a las variables del paquete, que
son todos "globales" para el paquete.

No tan simbólico referencias
Los corchetes alrededor de una referencia simbólica pueden servir simplemente para aislar un identificador o una variable
nombre del resto de una expresión, como siempre lo tienen dentro de una cadena. Para
ejemplo,

$ push = "pop on";
imprimir "$ {empujar} encima";

siempre ha tenido la intención de imprimir "pop on over", aunque empujar es una palabra reservada. Este es
generalizado para trabajar igual sin las comillas dobles adjuntas, de modo que

imprimir $ {empujar}. "sobre";

e incluso

imprimir $ {empujar}. "sobre";

tendrá el mismo efecto. Esta construcción es No considerado como una referencia simbólica
cuando estás usando referencias estrictas:

use 'refs' estrictos;
$ {palabra desnuda}; # Está bien, significa $ bareword.
$ {"bareword"}; # Error, referencia simbólica.

Del mismo modo, debido a todos los subíndices que se realizan con palabras sueltas, la misma regla
se aplica a cualquier palabra básica que se utilice para suscribir un hash. Así que ahora, en lugar de escribir

$ matriz {"aaa"} {"bbb"} {"ccc"}

puedes escribir solo

$ matriz {aaa} {bbb} {ccc}

y no se preocupe si los subíndices son palabras reservadas. En el raro caso de que
deseo hacer algo como

$ matriz {turno}

puede forzar la interpretación como una palabra reservada agregando cualquier cosa que la haga más que
una palabra desnuda:

$ matriz {turno ()}
$ array {+ shift}
$ matriz {shift @_}

El pragma "use advertencias" o el -w El interruptor le advertirá si interpreta una palabra reservada
como una cuerda. Pero ya no le advertirá sobre el uso de palabras en minúsculas, porque el
la cadena está efectivamente entre comillas.

Pseudo-hashes: Usando an matriz as a hachís
Se han eliminado los pseudo-hashes de Perl. El pragma 'campos' permanece disponible.

Función Plantillas
Como se explicó anteriormente, una función anónima con acceso a las variables léxicas visibles
cuando se compiló esa función, crea un cierre. Conserva el acceso a esas variables
aunque no se ejecuta hasta más tarde, como en un manejador de señales o una devolución de llamada Tk.

Usar un cierre como plantilla de función nos permite generar muchas funciones que actúan
similar. Suponga que desea funciones con el nombre de los colores que generaron la fuente HTML
cambios para los distintos colores:

imprimir "Ser", rojo ("cuidado"), "con eso", verde ("luz");

La planta de rojo() y verde() las funciones serían similares. Para crear estos, asignaremos un cierre
a un typeglob del nombre de la función que estamos intentando construir.

@colors = qw (rojo azul verde amarillo naranja violeta violeta);
para mi $ nombre (@colors) {
sin "referencias" estrictas; # permitir la manipulación de la tabla de símbolos
* $ nombre = * {uc $ nombre} = sub {" @_ "};
}

Ahora todas esas funciones diferentes parecen existir de forma independiente. Puedes llamar rojo(),
ROJO(), azul(), AZUL(), verde(), etc. Esta técnica ahorra tiempo de compilación y memoria
use, y también es menos propenso a errores, ya que las comprobaciones de sintaxis se realizan en tiempo de compilación. Es
crítico que cualquier variable en la subrutina anónima sea léxica con el fin de crear una
cierre adecuado. Esas son las razones de la variable de iteración "my" en el bucle.

Este es uno de los únicos lugares donde dar un prototipo a un cierre tiene mucho sentido. Si
deseaba imponer un contexto escalar en los argumentos de estas funciones (probablemente no un
sabia idea para este ejemplo en particular), podría haberlo escrito de esta manera en su lugar:

* $ nombre = sub ($) {" $ _ [0] "};

Sin embargo, dado que la verificación del prototipo ocurre en tiempo de compilación, la asignación anterior ocurre
demasiado tarde para ser de mucha utilidad. Puede abordar esto poniendo todo el ciclo de
asignaciones dentro de un bloque BEGIN, lo que obliga a que ocurra durante la compilación.

Acceso a léxicos que cambian con el tiempo, como los del ciclo "for" anterior, básicamente
alias a elementos de los ámbitos léxicos circundantes: solo funciona con subs anónimos,
no con subrutinas nombradas. Generalmente dicho, las subrutinas nombradas no se anidan correctamente y
solo debe declararse en el alcance del paquete principal.

Esto se debe a que las subrutinas con nombre se crean en tiempo de compilación, por lo que sus variables léxicas
se asignan a los léxicos padre desde la primera ejecución del bloque padre. Si un
El alcance principal se ingresa por segunda vez, sus léxicos se crean nuevamente, mientras que el anidado
los subs todavía hacen referencia a los antiguos.

Las subrutinas anónimas capturan cada vez que ejecuta el operador "sub", ya que son
creado sobre la marcha. Si está acostumbrado a utilizar subrutinas anidadas en otra programación
idiomas con sus propias variables privadas, tendrá que trabajar un poco en Perl. los
la codificación intuitiva de este tipo de cosas genera misteriosas advertencias sobre "no se quedará
shared "debido a las razones explicadas anteriormente. Por ejemplo, esto no funcionará:

sub externo {
mi $ x = $ _ [0] + 35;
sub interno {return $ x * 19} # INCORRECTO
return $ x + inner ();
}

Una solución alternativa es la siguiente:

sub externo {
mi $ x = $ _ [0] + 35;
local * inner = sub {return $ x * 19};
return $ x + inner ();
}

Ahora interno() solo se puede llamar desde dentro exterior(), debido a las asignaciones temporales
de la subrutina anónima. Pero cuando lo hace, tiene acceso normal al léxico.
variable $ x del alcance de exterior() en el momento en que se invoca a lo externo.

Esto tiene el interesante efecto de crear una función local a otra función,
algo que normalmente no es compatible con Perl.

ADVERTENCIA


No puede (útilmente) usar una referencia como clave para un hash. Se convertirá en un
cuerda:

$ x {\ $ a} = $ a;

Si intenta desreferenciar la clave, no hará una desreferenciación estricta, y no lo hará.
lograr lo que está intentando. Quizás quieras hacer algo más como

$ r = \ @a;
$ x {$ r} = $ r;

Y luego al menos puedes usar el valores (), que serán referencias reales, en lugar de las
llaves(), que no lo hará.

El módulo estándar Tie :: RefHash proporciona una solución conveniente para esto.

Sufijo Desreferencia Sintaxis


A partir de la v5.20.0, está disponible una sintaxis de sufijo para usar referencias. Se comporta como
descrito en "Uso de referencias", pero en lugar de un sigilo prefijado, un sigilo-y-
se utiliza estrella.

Por ejemplo:

$ r = \ @a;
@b = $ r -> @ *; # equivalente a @ $ r o @ {$ r}

$ r = [1, [2, 3], 4];
$ r -> [1] -> @ *; # equivalente a @ {$ r -> [1]}

Esta sintaxis debe estar habilitada con "use feature 'postderef'". Es experimental y
advertir de forma predeterminada a menos que "no hay advertencias 'experimental :: postderef'" en vigor.

La desreferencia de sufijo debería funcionar en todas las circunstancias en las que la desreferencia de bloque (circunferencia)
trabajado, y debe ser completamente equivalente. Esta sintaxis permite escribir la desreferenciación
y leer completamente de izquierda a derecha. Se definen las siguientes equivalencias:

$ sref -> $ *; # igual que $ {$ sref}
$ aref -> @ *; # igual que @ {$ aref}
$ aref -> $ # *; # igual que $ # {$ aref}
$ href ->% *; # igual que% {$ href}
$ cref -> & *; # igual que & {$ cref}
$ gref -> **; # igual que * {$ gref}

Tenga en cuenta especialmente que "$ cref -> & *" es No equivalente a "$ cref -> ()" y puede servir diferentes
propósitos.

Los elementos Glob se pueden extraer mediante la función de desreferenciación de postfijos:

$ gref -> * {ESCALAR}; # igual que * {$ gref} {ESCALAR}

Matriz de postfijos y desreferenciación escalar can utilizarse en la interpolación de cadenas (comillas dobles
o el operador "qq"), pero solo si la función adicional "postderef_qq" está habilitada.

Sufijo Referencias El rebanar
Las porciones de valor de matrices y hashes también se pueden tomar con notación de desreferenciación de postfijo,
con las siguientes equivalencias:

$ aref -> @ [...]; # igual que @ $ aref [...]
$ href -> @ {...}; # igual que @ $ href {...}

Rebanado de par clave / valor de Postfix, agregado en 5.20.0 y documentado en el Hash de clave / valor
La sección Slices de perldata también se comporta como se esperaba:

$ aref ->% [...]; # igual que% $ aref [...]
$ href ->% {...}; # igual que% $ href {...}

Al igual que con la matriz de postfijo, desreferenciación de rebanada de valor de postfijo can ser utilizado en la interpolación
cadenas (comillas dobles o el operador "qq"), pero solo si el "postderef_qq" adicional
la función está habilitada.

Asignando a Referencias


A partir de la v5.22.0, se puede asignar al operador de referencia. Realiza una
operación de alias, de modo que el nombre de la variable al que se hace referencia en el lado izquierdo se convierte en un
alias para la cosa a la que se hace referencia en el lado derecho:

\ $ a = \ $ b; # $ ay $ b ahora apuntan al mismo escalar
\ & foo = \ & bar; # foo () ahora significa bar ()

Esta sintaxis debe estar habilitada con "use feature 'refaliasing'". Es experimental y
advertirá de forma predeterminada a menos que "no hay advertencias 'experimental :: refaliasing'" en vigor.

Estos formularios pueden asignarse y hacer que el lado derecho se evalúe en formato escalar.
contexto:

\ $ escalar
\@formación
\%picadillo
\&sub
\ my $ escalar
\ my @array
\ my% hash
\ estado $ escalar # o @array, etc.
\ nuestro $ escalar # etc.
\ local $ escalar # etc.
\ local nuestro $ escalar # etc.
\ $ some_array [$ index]
\ $ some_hash {$ clave}
\ local $ some_array [$ index]
\ local $ some_hash {$ clave}
condición? \ $ esto: \ $ eso [0] # etc.

Las operaciones de corte y los paréntesis hacen que el lado derecho se evalúe en la lista
contexto:

\ @array [5..7]
(\ @array [5..7])
\ (@ matriz [5..7])
\ @hash {'foo', 'bar'}
(\ @hash {'foo', 'bar'})
\ (@ hash {'foo', 'bar'})
(\ $ escalar)
\ ($ escalar)
\ (mi $ escalar)
\ my ($ escalar)
(\@formación)
(\%picadillo)
(\&sub)
\(&sub)
\ ($ foo, @bar,% baz)
(\ $ foo, \ @bar, \% baz)

Cada elemento del lado derecho debe ser una referencia a un dato del tipo correcto.
Los paréntesis que rodean inmediatamente a una matriz (y posiblemente también
"mi" / "estado" / "nuestro" / "local") hará que cada elemento de la matriz sea un alias para el
escalar correspondiente referenciado en el lado derecho:

\ (@ a) = \ (@ b); # @a y @b ahora tienen los mismos elementos
\ mi (@a) = \ (@ b); # igualmente
\ (mi @a) = \ (@ b); # igualmente
empujar @a, 3; # pero ahora @a tiene un elemento extra del que carece @b
\ (@ a) = (\ $ a, \ $ b, \ $ c); # @a ahora contiene $ a, $ by $ c

Combinar ese formulario con "local" y poner paréntesis inmediatamente alrededor de un hash son
prohibido (porque no está claro qué deben hacer):

\ local (@array) = foo (); # INCORRECTO
\ (% hash) = barra (); # incorrecto

La asignación a referencias y no referencias se puede combinar en listas y condicional
expresiones ternarias, siempre que los valores del lado derecho sean del tipo correcto para
cada elemento de la izquierda, aunque esto puede generar un código ofuscado:

(mi $ tom, \ mi $ pene, \ mi @harry) = (\ 1, \ 2, [1..3]);
# $ tom es ahora \ 1
# $ dick ahora tiene 2 (solo lectura)
# @harry es (1,2,3)

mi $ tipo = ref $ cosita;
($ tipo? $ tipo == 'ARRAY'? \ @foo: \ $ bar: $ baz) = $ cosita;

El bucle "foreach" también puede tomar un constructor de referencia para su variable de bucle, aunque el
la sintaxis se limita a uno de los siguientes, con un "mi", "estado" o "nuestro" opcional después
la barra invertida:

\ $ s
\@un
\% h
\&C

No se permiten paréntesis. Esta función es particularmente útil para matrices de matrices,
o matrices de hashes:

foreach \ my @a (@array_of_arrays) {
frobnicar ($ a [0], $ a [-1]);
}

foreach \ my% h (@array_of_hashes) {
$ h {gelastic} ++ if $ h {type} == 'gracioso';
}

ADVERTENCIA: El aliasing no funciona correctamente con cierres. Si intentas alias léxico
variables de una subrutina interna o "eval", el alias solo será visible dentro de
ese sub interno, y no afectará a la subrutina externa donde se declaran las variables.
Este comportamiento extraño está sujeto a cambios.

Utilice perlref en línea utilizando los servicios de onworks.net


Servidores y estaciones de trabajo gratuitos

Descargar aplicaciones de Windows y Linux

Comandos de Linux

Ad




×
Anuncio
❤ ️Compre, reserve o adquiera aquí: sin costo, ayuda a mantener los servicios gratuitos.