Перебирать строку и удалять букву

Ошибки указывают на аппаратную проблему с диском, но только в секторах, содержащих данные.

Причина, по которой в Windows вы не видите этих ошибок (до сих пор), вероятно, связана с различием в программном обеспечении для просмотра файлов: большинство файловых браузеров Linux считывают больше информации о файлах, из файла при открытии папки, чем Проводник Windows. Это делается для того, чтобы сделать предварительный просмотр и получить метаданные для файлов. Windows, вероятно, получает это только по явному запросу.

Вы можете попробовать и посмотреть, сможете ли вы скопировать все файлы под Windows на отдельный диск. Если это сработает, запустите тщательный анализатор диска на исходном диске, прежде чем продолжить его использование (после создания полной резервной копии).

0
20.05.2018, 14:13
2 ответа

Eliminar letras de cadenas es fácil de hacer de una sola vez sin iterar sobre los caracteres de la cadena. Esto podría hacerse con trasí:

#!/bin/sh

perms="$( printf '%s' "$1" | tr -c -d 'rwx' )"

chmod u+"$perms" "$2"

Esto usa trpara eliminar primero todo del argumento de la primera línea de comando que no sea ninguno de los caracteres r, wo x, luego ejecuta chmod.

Tenga en cuenta la cita de las expansiones, especialmente "$2". Sin estas comillas, no podría usar su secuencia de comandos en archivos con espacios o caracteres de nombre de archivo en sus nombres (, consulte p. " ¿Por qué mi script de shell se ahoga con espacios en blanco u otros caracteres especiales? " ).

En bash, puede usar una sustitución de parámetro como

perms=${1//[!rwx]/}

Esto elimina todo lo que no es r, wo xde $1y asigna el resultado a perms.

El guión bashse convierte en

#!/bin/bash
chmod u+"${1//[!rwx]/}" "$2"

Usando

shift
chmod u+"$perms" "$@"

donde $permsse calcula de cualquiera de las formas anteriores(antes de el shift), incluso podría hacer que su secuencia de comandos realice el cambio en varios archivos a la vez. El shiftelimina el primer argumento de la línea de comando de la lista y "$@"se expandirá al resto de los argumentos,cada uno citado individualmente.


Si necesita absolutamente iterar sobre los caracteres de la cadena (no ), entonces puede hacerlo así:

#!/bin/bash

string="$1"

for (( i = 0; i < ${#string}; ++i )); do
    ch="${string:i:1}"
    if [[ "$ch" == [rwx] ]] && [[ "$new_string" != *$ch* ]]; then
        new_string+=$ch
    fi
done

printf 'The new string is "%s"\n' "$new_string"

Esto construye una nueva cadena a partir de la anterior agregando r, wo xsi el carácter actual en la cadena original es uno de esos caracteres, y si el el carácter aún no existe en la nueva cadena (no es necesario para la operación dechmod).

En lugar de usar seq, usamos un bucle forque va de cero a uno menos que la longitud de la cadena original, y para facilitar la lectura y no repetirnos, extraemos el carácter actual en chen cada iteración.

En lugar de tres pruebas en el carácter, realizamos una sola coincidencia de patrón para ver si es r, wo x.

4
28.01.2020, 02:15

${permisos/perm_actual/}elimina la cadena literal perm_actualdel valor de la variable, creo que quiere ${permisos/$perm_actual/}en su lugar.

Pero podría usar permisos=${permisos//[^rwx]}en lugar del bucle para eliminar todos los caracteres que no sean-rwxde una sola vez, y [[ $permisos = *[^rwx]* ]]para verificar si la variable tiene alguno de ellos.

(Tanto ${foo//bar}como [[.. ]]son ​​extensiones no estándar, pero ya las usó, por lo que probablemente esté ejecutando Bash/ksh/zsh.)

2
28.01.2020, 02:15

Теги

Похожие вопросы