@mattdm El uso lsno funcionará si uno de los nombres de archivo contiene un espacio en blanco.
helpermethod
2
¿Cómo se define la palabra ? Si el primer archivo es Sunset on a beach.jpg, ¿debería serlo Sunseto el nombre completo del archivo? ¿Qué hay de Sea, sex and sun.ogg? Sea, Sea,O la totalidad nombre de archivo?
Stéphane Chazelas
@mattdm ls | head -1me da cosas aleatorias como a.patch p.pycuál no es la primera palabra y ni siquiera los archivos en orden alfabético.
phuclv
Respuestas:
52
Puedes canalizarlo a través de awk y hacer que se haga eco de la primera palabra
echo *| head -n1 | awk '{print $1;}'
o cortas la cadena y seleccionas la primera palabra:
echo *| head -n1 | cut -d " "-f1
o lo canalizas a través de sed y haces que elimine todo menos la primera palabra
echo *| head -n1 | sed -e 's/\s.*$//'
Se agregó el | head -n1para satisfacer a los nitpickers. En caso de que su cadena contenga nuevas | head -n1líneas, primero seleccionará la primera línea antes de que los comandos importantes seleccionen la primera palabra de la cadena que se le pasó.
El devolvería la primera palabra de cada línea, no la primera palabra.
Stéphane Chazelas
2
echo *
Me
Eso depende de cuántos archivos tengan caracteres de nueva línea en su nombre o según el entorno o cómo se compiló bash o si algún archivo llamado -eo -ee... aparece en la lista, cuántas veces \naparece en un nombre de archivo. Si hay un archivo llamado -n, es posible que ni siquiera devuelva ninguna línea ...
Stéphane Chazelas
Bueno, todavía estamos hablando de bash y 1. generalmente bash no pasará una cadena con líneas nuevas como una cadena con líneas nuevas 2. es muy difícil e inusual (¿imposible?) Tener una nueva línea en un nombre de archivo 3. a \ n en un nombre de archivo aparecerá como \ n 4. 3 retenciones para nombres de archivo que comienzan con - 5. incluso cuando se llama con -n o -e echo se abrirá stdout y se cerrará cuando esté hecho, por supuesto, devolverá una línea, y en al menos una cadena, para el caso 6.
edité
1
Los 5 puntos son falsos. Pruebe en un directorio vacío: touch '$a\nb' 'a\nb'; env BASHOPTS=xpg_echo bash -c 'echo * | wc -l'( xpg_echoestá habilitado donde bashsea necesario para ser compatible con Unix). Y en otro directorio vacío: touch ./-n; bash -c 'echo * | wc -l'. Una línea es una secuencia de caracteres terminados por un carácter de nueva línea. Si echono genera un carácter de nueva línea, no genera ninguna línea. El comportamiento de las utilidades de texto como cut, awko sedno se especifica si la entrada tiene caracteres adicionales después del último carácter de nueva línea y el comportamiento varía según las implementaciones.
Stéphane Chazelas
18
Asumiendo un shell posixy ( /bin/sho /bin/bashpuede hacer esto)
all=$(echo *)
first=${all%%*}
La construcción ${all%% *}es un ejemplo de eliminación de subcadenas . Los %%medios eliminan la coincidencia más larga de *(un espacio seguido de cualquier cosa) desde el extremo derecho de la variable all. Puedes leer más sobre la manipulación de cadenas aquí .
Esta solución supone que el separador es un espacio. Si está haciendo esto con nombres de archivo, cualquiera con espacios lo romperá.
Buena esa. Pero me gustó la otra versión simple y más no hacky con headycut
Anwar
44
OMI, cabeza, corte y sed son menos simples. ¿Por qué generar otra herramienta cuando la sustitución de parámetros incorporados hace el trabajo de manera eficiente? Esta respuesta es la forma más eficiente y portátil de elegir la primera palabra de una lista de palabras separadas por espacios (que es todo lo que solicitó el OP).
Juan
7
Suponiendo que realmente desea el primer nombre de archivo y no la primera palabra , aquí hay una forma que no se rompe en espacios en blanco:
Tenga en cuenta que esto destruirá cualquier otro argumento de su script, a menos que se ejecute en un ámbito auxiliar. También se expandirá a *si no hay archivos en el directorio.
ls
no funcionará si uno de los nombres de archivo contiene un espacio en blanco.Sunset on a beach.jpg
, ¿debería serloSunset
o el nombre completo del archivo? ¿Qué hay deSea, sex and sun.ogg
?Sea
,Sea,
O la totalidad nombre de archivo?ls | head -1
me da cosas aleatorias comoa.patch p.py
cuál no es la primera palabra y ni siquiera los archivos en orden alfabético.Respuestas:
Puedes canalizarlo a través de awk y hacer que se haga eco de la primera palabra
o cortas la cadena y seleccionas la primera palabra:
o lo canalizas a través de sed y haces que elimine todo menos la primera palabra
Se agregó el
| head -n1
para satisfacer a los nitpickers. En caso de que su cadena contenga nuevas| head -n1
líneas, primero seleccionará la primera línea antes de que los comandos importantes seleccionen la primera palabra de la cadena que se le pasó.fuente
echo *
-e
o-ee
... aparece en la lista, cuántas veces\n
aparece en un nombre de archivo. Si hay un archivo llamado-n
, es posible que ni siquiera devuelva ninguna línea ...touch '$a\nb' 'a\nb'; env BASHOPTS=xpg_echo bash -c 'echo * | wc -l'
(xpg_echo
está habilitado dondebash
sea necesario para ser compatible con Unix). Y en otro directorio vacío:touch ./-n; bash -c 'echo * | wc -l'
. Una línea es una secuencia de caracteres terminados por un carácter de nueva línea. Siecho
no genera un carácter de nueva línea, no genera ninguna línea. El comportamiento de las utilidades de texto comocut
,awk
osed
no se especifica si la entrada tiene caracteres adicionales después del último carácter de nueva línea y el comportamiento varía según las implementaciones.Asumiendo un shell posixy (
/bin/sh
o/bin/bash
puede hacer esto)La construcción
${all%% *}
es un ejemplo de eliminación de subcadenas . Los%%
medios eliminan la coincidencia más larga de*
(un espacio seguido de cualquier cosa) desde el extremo derecho de la variableall
. Puedes leer más sobre la manipulación de cadenas aquí .Esta solución supone que el separador es un espacio. Si está haciendo esto con nombres de archivo, cualquiera con espacios lo romperá.
fuente
head
ycut
Suponiendo que realmente desea el primer nombre de archivo y no la primera palabra , aquí hay una forma que no se rompe en espacios en blanco:
fuente
files=($(echo *))
bash
se compiló o del entorno, posiblemente en caracteres de barra invertida.text=$(echo *); set -f; files=($text)
contrario, se podrían expandir más comodines.files=$(echo *); echo ${files%% *}
Puedes usar los parámetros posicionales
fuente
*
si no hay archivos en el directorio.shopt -s nullglob
manejaría esoMarque una de las siguientes alternativas:
Luego puede imprimirlo a través de
echo $FILE
.Ver también: ¿
grep
la única primera palabra de la salida?fuente
Esto funciona:
Créditos a https://unix.stackexchange.com/a/57879/3920
fuente
Obteniendo todo el primer nombre de archivo:
fuente