Risposte:
head
funziona anche:
head -c 100 file # returns the first 100 bytes in the file
.. estrarrà i primi 100 byte e li restituirà.
La cosa bella dell'uso head
per questo è che la sintassi per le tail
corrispondenze:
tail -c 100 file # returns the last 100 bytes in the file
Puoi combinarli per ottenere intervalli di byte. Ad esempio, per ottenere i secondi 100 byte da un file, leggi i primi 200 con head
e usa tail per ottenere gli ultimi 100:
head -c 200 file | tail -c 100
head
, quindi usa tail
per ottenere gli ultimi 10, ad esempio:head -c 20 file | tail -c 10
È possibile utilizzare dd per estrarre blocchi arbitrari di byte.
Per esempio,
dd skip=1234 count=5 bs=1
copierebbe i byte da 1235 a 1239 dal suo input al suo output e scarterebbe il resto.
Per ottenere solo i primi cinque byte dallo standard input, eseguire:
dd count=5 bs=1
Nota che, se vuoi specificare il nome del file di input, dd ha un'analisi degli argomenti vecchio stile, quindi dovresti fare:
dd count=5 bs=1 if=filename
Nota anche che dd annuncia verbalmente quello che ha fatto, quindi per buttarlo via, fai:
dd count=5 bs=1 2>&-
o
dd count=5 bs=1 2>/dev/null
dd bs=1
costringe dd a leggere e scrivere un singolo carattere alla volta, il che è molto più lento di head
quando il conteggio è grande. Tuttavia, non si nota per count = 5.
dd
, a quanto pare, farà il trucco .. Salute!
head -c
dd bs=5 count=1
testa :
head - visualizza la prima parte dei file
head [ OPZIONE ] ... [ FILE ] ...
Stampa le prime 10 righe di ogni FILE sullo standard output. Con più di un FILE, far precedere ciascuno da un'intestazione che dia il nome del file. Senza FILE, o quando FILE è -, leggi lo standard input.
Gli argomenti obbligatori per le opzioni lunghe sono obbligatori anche per le opzioni brevi.
-c , --bytes = [-] N
stampa i primi N byte di ogni file; con il '-' iniziale, stampa tutti tranne gli ultimi N byte di ogni file
head -Line_number file_name | tail -1 |cut -c Num_of_chars
questo script fornisce il numero esatto di caratteri dalla riga e dalla posizione specifiche, ad esempio:
head -5 tst.txt | tail -1 |cut -c 5-8
fornisce i caratteri nella riga 5 e i caratteri da 5 a 8 della riga 5,
Nota : tail -1
serve per selezionare l'ultima riga visualizzata dalla testa.
potresti anche estrarre la linea e poi tagliarla come ad esempio:
nomefile grep 'text' | tagliare -c 1-5
So che la risposta è in risposta a una domanda posta 6 anni fa ...
Ma stavo cercando qualcosa di simile per alcune ore e poi ho scoperto che: cut -c fa esattamente questo, con un ulteriore vantaggio che potresti anche specificare un offset.
cut -c 1-5 restituirà Hello e cut -c 7-11 restituirà world . Non c'è bisogno di altri comandi
Anche se questo è stato risposto / accettato anni fa, la risposta attualmente accettata è corretta solo per le codifiche di un byte per carattere come iso-8859-1, o per i sottoinsiemi a byte singolo di set di caratteri a byte variabile (come i caratteri latini all'interno di UTF-8). Anche l'utilizzo di giunzioni a più byte invece funzionerebbe ancora solo per codifiche multibyte fisse come UTF-16. Dato che ora UTF-8 è sulla buona strada per diventare uno standard universale, e quando si guarda questo elenco di lingue per numero di madrelingua e questo elenco delle prime 30 lingue per utilizzo nativo / secondario , è importante sottolineare un semplice tecnica a byte variabile (non basata su byte), che utilizza cut -c
e tr
/ sed
con classi di caratteri.
Confronta quanto segue che doppiamente fallisce a causa di due comuni errori / presunzioni latini riguardanti il problema dei byte rispetto ai caratteri (uno è head
contro cut
, l'altro è [a-z][A-Z]
contro [:upper:][:lower:]
):
$ printf 'Πού μπορώ να μάθω σανσκριτικά;\n' | \
$ head -c 1 | \
$ sed -e 's/[A-Z]/[a-z]/g'
[[unreadable binary mess, or nothing if the terminal filtered it]]
a questo (nota: questo ha funzionato bene su FreeBSD, ma entrambi cut
e tr
su GNU / Linux hanno ancora alterato il greco in UTF-8 per me):
$ printf 'Πού μπορώ να μάθω σανσκριτικά;\n' | \
$ cut -c 1 | \
$ tr '[:upper:]' '[:lower:]'
π
Un'altra risposta più recente aveva già proposto il "taglio", ma solo per il problema secondario che può essere utilizzato per specificare offset arbitrari, non per il problema direttamente rilevante tra caratteri e byte.
Se cut
non -c
gestisci correttamente le codifiche a byte variabile, per "i primi X
caratteri" (sostituisci X
con il tuo numero) potresti provare:
sed -E -e '1 s/^(.{X}).*$/\1/' -e q
- che è però limitato alla prima rigahead -n 1 | grep -E -o '^.{X}'
- che è limitato alla prima riga e concatena due comandidd
- che è già stato suggerito in altre risposte, ma è davvero macchinososed
script complicato con buffer della finestra scorrevole per gestire i caratteri distribuiti su più righe, ma probabilmente è più ingombrante / fragile del semplice utilizzo di qualcosa di similedd
Se tr
non gestisci correttamente le classi di caratteri con codifiche a byte variabili, potresti provare:
sed -E -e 's/[[:upper:]]/\L&/g
(GNU-specifico)printf 'Πού ' | cut -c 1
restituisce solo
Ecco un semplice script che si conclude utilizzando l' dd
approccio menzionato qui:
#!/usr/bin/env bash
function show_help()
{
IT="
extracts characters X to Y from stdin or FILE
usage: X Y {FILE}
e.g.
2 10 /tmp/it => extract chars 2-10 from /tmp/it
EOF
"
echo "$IT"
exit
}
if [ "$1" == "help" ]
then
show_help
fi
if [ -z "$1" ]
then
show_help
fi
FROM=$1
TO=$2
COUNT=`expr $TO - $FROM + 1`
if [ -z "$3" ]
then
dd skip=$FROM count=$COUNT bs=1 2>/dev/null
else
dd skip=$FROM count=$COUNT bs=1 if=$3 2>/dev/null
fi
mkfifo /tmp/test.fifo; echo "hello world">/tmp/test.fifo & head -c 5 /tmp/test.fifo
consuma anche" world\n"
che si perde per sempre.