부동 소수점 정규 표현식만 허용됩니다.

부동 소수점 정규 표현식만 허용됩니다.

특정 문자열이 부동 소수점인지 확인하는 방법은 무엇입니까? 이는 부동 소수점으로 가능합니다.

12.245
+.0009
3.11e33
43.1E11
2e-14

내가 시도한 것은 다음과 같습니다.

grep "^[+\-\.0-9]" 
grep "^[+-]*[0-9]"
grep "^[+\-\.0-9]" 

다른 관련 내용이 많이 있지만 전혀 필터링되지 않습니다. 거의 모든 문자열이 교차됩니다. 이 문제를 어떻게 해결할 수 있나요?

답변1

grep -xE '[-+]?[0123456789]*\.?[0123456789]+([eE][-+]?[0123456789]+)?'

를 사용하여 -x줄의 시작과 위치에 정규식을 고정하므로 줄의 어느 곳에서나 패턴이 발견되는 것이 아니라 줄이 전체 패턴과 일치해야 합니다.

지원되는 모든 항목을 일치시키려면POSIX/Cstrtod()이 유틸리티의 많은 구현에서 인식되는 바와 같이 printf예를 들면 다음과 같습니다.

r=[$(locale decimal_point)]
d=[0123456789]
h=[0123456789abcdefABCDEF]
grep -xE "[[:space:]]*[-+]?($d*$r?$d+([eE][-+]?$d+)?|\
0[xX]$h*$r?$h*([pP][-+]?$d+)?|\
[iI][nN][fF]([iI][nN][iI][tT][yY])?|\
[nN][aA][nN]|\
NAN\([abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_]+\))"

0x3f, 0xFP-4, -Infinity, NAN(무엇이든)과 같은 것들도 마찬가지입니다.

$ printf '%g\n' 0x3f 0xFp-4 -Infinity 'NAN(whatever)'
63
0.9375
-inf
nan

답변2

선택하다파이썬솔루션(용더 적은복잡한 입력):

샘플 input.txt파일:

11
12.245
+.0009
---0
3.11e33
43.1E11
2e-14
t12
aaa
10.001

check_float.py스크립트:

import sys

with open(sys.argv[1], 'r') as inp:
    f = 'No'
    for l in inp.read().splitlines():
        try:
            if float(l) and '.' in l: f = 'Yes'
        except ValueError:
            f = 'No'
        finally:
            print '{0} - {1}'.format(l, f)

용법:

python check_float.py input.txt

산출:

11 - No
12.245 - Yes
+.0009 - Yes
---0 - No
3.11e33 - Yes
43.1E11 - Yes
2e-14 - Yes
t12 - No
aaa - No
10.001 - Yes

답변3

면책조항: 이는 불완전한 솔루션입니다. Perl의 Scalar::Util::looks_like_number()기능은 이를 수행하는 최선의 루틴 선택이 아닐 수도 있습니다. 바라보다Stéphane Chazelas는 아래에 댓글을 달았습니다..

누군가 그것을 보고 뭔가를 고르고 싶다면 coproc여기에 남겨 두겠습니다.


가능한 많은 부동 소수점 형식과 일치하도록 자신만의 정규 표현식을 작성하는 대신 이미 구현된 라이브러리를 사용하십시오.

perl -MScalar::Util -ne 'exit !Scalar::Util::looks_like_number($_)'

bash쉘 함수 로서 :

is_number () {
    perl -MScalar::Util -ne 'exit !Scalar::Util::looks_like_number($_)' <<<"$1"
}

is_number hello && echo 'hello is a number'
is_number 1.234 && echo '1.234 is a number'

bash공동 프로세스 로 (숫자를 테스트할 때마다 Perl 프로세스를 시작하지 않기 위해):

coproc PERLIO=:raw perl -MScalar::Util -ne \
    'print Scalar::Util::looks_like_number($_) ? "Yes" : "No", "\n"'

while IFS= read -r -p 'Number please: ' possnum; do
    printf '%s\n' "$possnum" >&${COPROC[1]}
    read -u ${COPROC[0]}

    case "$REPLY" in
        Yes)    printf '%s is a number\n' "$possnum"       ;;
        No)     printf '%s is _not_ a number\n' "$possnum" ;;
    esac
done

kill "$COPROC_PID"

또는 두 가지를 결합합니다.

coproc PERLIO=:raw perl -MScalar::Util -ne \
    'print Scalar::Util::looks_like_number($_) ? "Yes" : "No", "\n"'

is_number () {
    printf '%s\n' "$1" >&${COPROC[1]}

    local REPLY
    read -u ${COPROC[0]}

    [ "$REPLY" = 'Yes' ] && return 0

    return 1
}

while IFS= read -r -p 'Number please: ' possnum; do
    if is_number "$possnum"; then
        printf '%s is a number\n' "$possnum"
    else
        printf '%s is a _not_ a number\n' "$possnum"
    fi
done

kill "$COPROC_PID"

관련 정보