Probar si la serie entera está aumentando estrictamente

1

Me gustaría probar si una lista de valores enteros (por ejemplo, almacenados en un archivo, uno por línea) está aumentando estrictamente, utilizando un script bash.

¿Hay alguna manera simple / concisa de lograr eso?

sdabet
fuente

Respuestas:

6

Compruebe si el contenido del archivo permanece igual después de ordenar numéricamente y filtrar líneas duplicadas:

cmp file <(sort -n file | uniq)

Al menos GNU sortpuede hacer esta verificación directamente:

sort -c -u -n file

(La documentación POSIX tambiénsort menciona esto, por lo que debería ser compatible en todas partes).

Stephen Kitt
fuente
Pero eso no funcionará para un aumento estricto , ¿verdad?
sdabet
@fiddler si omite la parte "filtrar líneas duplicadas" obtendrá su solución para una secuencia estrictamente creciente
roaima
La sortsolución parece perfecta.
sdabet
Tenga en cuenta que la ordenación GNU (a diferencia de la ordenación Solaris, por ejemplo) parece leer la entrada completamente antes de informar el trastorno, incluso si el trastorno está en la segunda línea.
Stéphane Chazelas
1
Sí, incluso cuando se verifica , comienza llenando un búfer .
Stephen Kitt
2

Si quiere decir, compruebe que cada línea es un entero decimal que es uno más el entero decimal en la línea anterior, luego:

awk 'NR == 1 {n = $0; next}
     $0 != n+1 {status = 1; exit}
     {n = $0}
     END {exit status}'

Reemplace $0 != n+1con $0 <= npara verificar el aumento estricto por cualquier valor, no solo uno. Sin embargo, en ese caso, probablemente prefiera el sort -cenfoque a menos que desee que deje de leer en el primer trastorno o desee admitir formatos de número (hexadecimal, notación de coma flotante ...) no admitidos sort(como cuando su ordenación no no apoyo -g)

Stéphane Chazelas
fuente
estrictamente creciente simplemente significa que para una secuencia entera, el valor actual es mayor que el anterior. No supone que esté aumentando en uno, o incluso en cualquier cantidad regular. Solo que cada número es la secuencia es más grande que la anterior.
roaima
1

Con awk:

awk 'length(p)&&++p!=$0{print "Not OK";exit};{p=$0}' file

para aumentar uno por línea. Para verificar la corriente es más grande que la anterior:

awk 'length(p)&&++p<=$0{print "Not OK";exit};{p=$0}' file
Cuonglm
fuente
0

La versión extremadamente concisa sería algo como esto

#!/bin/bash
awk 'NR > 1 && $1 < prev { printf( "error at line %d\n", NR); exit; } { prev = $1 } '  $1

Este código no conciso sería

#!/bin/bash
l=1     #line number count
p=0     #previous line value
for f in `cat $1`
do
    if [ \( "$f" -lt "$p" \) -a \( "$l" -ne "1" \) ]   #chk for all lines, except first
        then    echo "$f is less than $p on Line $l"
        break
    else
        p=$f  #set previous
    fi
    l=$(expr $l + 1)   #increment line number
done
amisax
fuente