Quindi questo mi ha fatto impazzire per l'ultima mezz'ora. C'è un modo per me di prendere una fetta di matrice alla fine di un array anonimo? Ho provato:
(split(' ',$test_line))[1..$#_]
e ho provato: (split(' ',$test_line))[1..-1]
ma aggravatingly, nessuno di questi lavori. Davvero non voglio avere un'ulteriore variabile temporanea istanziata per l'array intermedio (che non ho bisogno). E davvero non voglio usare un rivestimento brutto e illeggibile (ne ho trovati alcuni online). Non c'è davvero un modo semplice per farlo?C'è qualche modo per prendere una fetta alla fine di un array anonimo in Perl?
risposta
Un elenco, che è quello che hai nel tuo esempio, non può essere affettato alla fine. Ciò è principalmente dovuto al fatto che le liste non sono strutture dati appropriate in Perl, ma più un costrutto che l'interprete usa per spostare i dati. Quindi, sapendo che puoi solo dividere un elenco dall'inizio, le tue opzioni sono o metterlo in una variabile di matrice e poi tagliare, cambiare l'algoritmo per restituire quello che vuoi, o il seguente:
Se stai assegnando questo il valore a qualcosa, è possibile utilizzare undef
in ogni slot non volete:
my (undef, @list) = split ' ' => $test_line;
Se pubblichi un po 'di codice, posso rivedere.
In alternativa, è possibile utilizzare alcuni strumenti dalla programmazione funzionale. La coppia di funzioni drop
e take
può essere utile per ridimensionare una lista senza ulteriori variabili:
sub take {
my $n = shift;
@_[0..$n-1]
}
sub drop {
my $n = shift;
@_[$n..$#_]
}
e quindi il vostro esempio diventa
drop 1, split ' ' => $test_line;
drop 1
è anche comunemente chiamato tail
sub tail {drop 1, @_}
e, naturalmente, dal momento che tutti questi sono così brevi, se si vuole in linea:
sub {shift; @_}->(split ' ' => ...)
La mia idea è sulla falsariga di: my% test_hash = (split ('', $ test_line)) [1 .. $ # _]; In questo caso particolare, il tuo approccio funziona bene, ma speravo in qualcosa di un po 'più generico, così che quando non desidero i primi 10 elementi, non sarò bloccato a scrivere undef 10 volte ... – Eli
@Eli => purtroppo non è una funzionalità delle sezioni di lista in perl5. La soluzione generica è qualcosa come 'drop' o' take'. A seconda del contenuto, potresti anche essere in grado di utilizzare grep per rimuovere gli elementi che non desideri. –
Bella risposta. Ci * sono * soluzioni one-liner, ma in realtà non appartengono al codice di produzione. – tchrist
Non credo è possibile specificare un indice per l'ultimo elemento di un'espressione elenco arbitrario, ma che ne dici:
split(' ', (split ' ', $test_line, 2)[1])
A proposito, non ci sono schiere anonime qui (o nella tua domanda originale), solo elenchi.
Quando l'OP ha detto fetta, ho pensato di splice
:
@allTheWordsExceptTheFirstTwo = splice @{[split' ', $test_line]}, 2;
@allExceptTheFirstAndLastTwo = splice @{[split' ', $test_line]}, 2, -2;
se siete aperti alla scissione due volte:
my @g = (split ' ', $test_str)[1..split(' ', $test_str)];
o più correttamente (in quanto diviso restituisce il numero di campi trovati (uno in più rispetto all'ultimo indice del campo poiché è a base 0):
my @g = (split ' ', $test_str)[1..split(' ', $test_str)-1];
sfortunatamente questi lanciano un avviso deprecato sotto il pragma "warnings" e nascondono il contenuto di @_ (a meno che non stiate usando 5.12, quindi sei bravo, altrimenti vai con una variabile temporanea, inline sub o un ciclo).
È possibile utilizzare intervalli negativi nel indice di matrice per risolvere un numero arbitrario di elementi dalla fine:
my $x = join ' ' => 'a' .. 'z';
my @x = (split ' ', $x)[-13 .. -1];
Tuttavia, ciò richiede di conoscere il numero totale di elementi nel risultato di split
eliminare solo il primo elemento.
Se questo accade in un solo luogo, utilizzando un blocco do
dovrebbe funzionare:
my $x = join ' ', 'a' .. 'z';
my @x = do { my @y = (split ' ', $x); @y[1 .. $#y] };
Nel tuo caso, vorrei scomporre l'intera operazione ad una subroutine se si suppone per essere utilizzato di frequente, passando la stringa piuttosto che il risultato del split
alla subroutine (può essere ulteriormente generalizzato consentendo all'utente di passare il modello di divisione così:
my $x = join ' ', 'a' .. 'g';
my @x = skip_first_n_from_split(3, $x);
print Dump \@x;
sub skip_first_n_from_split {
my ($n, $x) = @_;
my @y = split ' ', $x;
return @y[$n .. $#y];
}
Having fun:
#!/usr/bin/perl
use strict; use warnings;
my $x = join ' ', 1 .. 8;
my @skippers = map make_skipper(' ', $_), 0 .. 7;
print "@$_\n" for map $_->($x), @skippers;
sub make_skipper {
my ($pattern, $n) = @_;
return sub {
my $string = shift;
my $i = 0;
return [ grep $i++ >= $n, split $pattern, $string ];
}
}
uscita:
1 2 3 4 5 6 7 8 2 3 4 5 6 7 8 3 4 5 6 7 8 4 5 6 7 8 5 6 7 8 6 7 8 7 8 8
Questo appena ricevuto answered 'ordinatamente' sul PerlMonks da BrowserUK, questo è quello che ci fa:
my @slice = sub{ @_[1..$#_] }->(split ' ', $test_line);
- 1. Come specificare una "fetta di coda" in Perl?
- 2. Perl: riferimento matrice contro array anonimo
- 3. Ottenere un puntatore alla fine di un array
- 4. equivalente sovrapposizione di Array # fetta
- 5. Come aggiungere un elemento alla fine di un array?
- 6. saltando una linea in un array, Perl
- 7. Cosa significa() alla fine della subroutine Perl?
- 8. Puoi prendere un riferimento a una funzione integrata in Perl?
- 9. Perl: taglia un array, senza creare un intero nuovo array
- 10. Incremento un numero intero alla fine di una stringa in Perl
- 11. Dichiarare una fetta o fare una fetta?
- 12. Come prendere input in un array + PYTHON?
- 13. C'è un modo per fermare il punto di riempimento alla fine di una frase?
- 14. Estrarre un iteratore Prendere in una tupla
- 15. Perl - Come ottenere il numero di elementi in un array anonimo, per tagliare concisamente i nomi di percorso
- 16. C'è un modo per creare un oggetto anonimo in PHP
- 17. Come si cerca un array Perl per una stringa corrispondente?
- 18. In Perl, come posso creare un hash le cui chiavi provengono da un determinato array?
- 19. perl beffa c'è un modo per deridere $?
- 20. Cosa significa "&" alla fine di un comando linux?
- 21. jQuery ha qualche funzione per far scorrere il client fino alla fine della porta di visualizzazione?
- 22. In Perl, c'è un modo per legare una scorta?
- 23. C'è un modo per precompilare una regex in Perl?
- 24. Come controllo una fetta vuota?
- 25. modo idiomatico di prendere una stringa di un ByteString
- 26. Leggere una matrice PostgreSQL direttamente in un Golang fetta
- 27. Lunghezza massima di una fetta di Go
- 28. Sposta un elemento alla fine dell'array
- 29. C'è un modo per prendere le prime 1000 righe di Spark Dataframe?
- 30. Punto e virgola Perl alla fine del prospetto
ho il sospetto la migliore risposta sarà l'extra variabile temporanea. Sulla prima riga, il motivo '$ # _' non funziona è che '@ _' non è la lista dall'espressione. – aschepler