So sánh một chuỗi bằng cách sử dụng sh shell


193

Tôi đang sử dụng SH shell và tôi đang cố gắng so sánh một chuỗi với giá trị của một biến nhưng ifđiều kiện luôn được thực thi thành true. Tại sao?

Đây là một số mã:

Sourcesystem="ABC"

if [ "$Sourcesystem" -eq 'XYZ' ]; then 
    echo "Sourcesystem Matched" 
else
    echo "Sourcesystem is NOT Matched $Sourcesystem"  
fi;

echo Sourcesystem Value is  $Sourcesystem ;

Ngay cả điều này không hoạt động:

Sourcesystem="ABC"

if [ 'XYZ' -eq "$Sourcesystem" ]; then 
    echo "Sourcesystem Matched" 
else
    echo "Sourcesystem is NOT Matched $Sourcesystem"  
fi;

echo Sourcesystem Value is  $Sourcesystem ;

Thứ hai, chúng ta có thể kết hợp điều này với một chuỗi NULL hoặc rỗng không?


Đầu tiên trong Bourne shell, bạn không cần thêm ';' Khi tôi chạy thử tập lệnh trong Bourne shell, điều kiện if là sai. Đầu tiên nó sẽ đưa ra cảnh báo: [: ABC: biểu thức số nguyên được mong đợi. Đầu ra là: "Hệ thống nguồn KHÔNG phù hợp với ABC". Như nhận xét của những người khác, -eq được sử dụng để so sánh số nguyên. Sử dụng một dấu bằng duy nhất để so sánh chuỗi trong Bourne shell (#! / Bin / sh). Vỏ của bạn nên đã sửa chữa bạn ngay từ đầu.
Kemin Zhou

6
Bỏ phiếu để mở lại. Các dups được trích dẫn dành cho bash shell, không phải sh thiếu máu mà đôi khi là Posix shell hoặc Dash.
jww

1
Đồng ý và bình chọn như vậy. shbashcó cùng mối quan hệ với CC++. Mặc dù mã được viết cho mã đầu tiên hợp lệ trong mã thứ hai, nhưng các câu trả lời cho mã thứ hai không thể tin cậy để hoạt động trong mã đầu tiên.
btilly

Câu trả lời:


283

Bạn nên sử dụng =toán tử để so sánh chuỗi:

Sourcesystem="ABC"

if [ "$Sourcesystem" = "XYZ" ]; then 
    echo "Sourcesystem Matched" 
else
    echo "Sourcesystem is NOT Matched $Sourcesystem"  
fi;

man testnói rằng bạn sử dụng -zđể so khớp cho các chuỗi trống.


2
Nó không cần thiết để trích dẫn ABChoặc XYZ.
thúc

29
Nếu biến của bạn có thể có khoảng trắng trong đó thì việc trích dẫn là cần thiết.
William Everett

1
Đã điều chỉnh ví dụ để làm cho phần đó rõ ràng hơn @WilliamEverett.
Per Lundberg


35

eq được sử dụng để so sánh các số nguyên thay vào đó sử dụng bằng '=', ví dụ:

if [ 'AAA' = 'ABC' ];
then 
    echo "the same" 
else 
    echo "not the same"
fi

chúc may mắn


Lưu ý: nếu bạn đang so sánh các biến, chắc chắn rằng bạn sử dụng "$VAR"và không chỉ đơn giản$VAR
Sridhar Sarnobat

21

Tôi đã gặp vấn đề tương tự, hãy làm điều này

if [ 'xyz' = 'abc' ];
then
echo "match"
fi

Chú ý khoảng trắng. Điều quan trọng là bạn phải sử dụng khoảng trắng trong trường hợp này sau và trước =dấu.

Kiểm tra " Các toán tử so sánh khác ".


1
trong Dockerfile: / bin / sh: 1: [: =: nhà điều hành không mong đợi
holms

10

-eqlà toán tử so sánh shell để so sánh các số nguyên. Để so sánh các chuỗi bạn cần sử dụng =.


5

-eqlà một toán tử so sánh toán học. Tôi chưa bao giờ sử dụng nó để so sánh chuỗi, dựa vào ==!=so sánh.

if [ 'XYZ' == 'ABC' ]; then   # Double equal to will work in Linux but not on HPUX boxes it should be if [ 'XYZ' = 'ABC' ] which will work on both
  echo "Match"
else
  echo "No Match"
fi

18
Lưu ý rằng toán tử ==không hoạt động trên mọi trình bao. =là toán tử chính xác để sử dụng để so sánh các chuỗi và ==đôi khi là một từ đồng nghĩa.
Omer Dagan

3

Trong số 4 shell mà tôi đã thử nghiệm, ABC -eq XYZđánh giá là true trong testnội trang cho zshksh. Biểu thức đánh giá thành false dưới /usr/bin/testvà nội trang cho dashbash. Trong kshzsh, các chuỗi được chuyển đổi thành các giá trị số và bằng nhau vì chúng đều bằng 0. IMO, hoạt động của các nội trang cho kshzshkhông chính xác, nhưng thông số kỹ thuật cho testlà không rõ ràng về điều này.


1
Cảm ơn bạn đã thử nghiệm. Đó là lý do tại sao Bourne shell được ưa chuộng.
Kemin Zhou

zsh kết quả rõ ràng : biểu thức số nguyên được mong đợi sau khi sử dụng [ hoặc kiểm tra nội trang . Có thể bạn đang buộc [[ đánh giá cả hai là 0 vì các chuỗi không phải là số nguyên đáng kể.
code933k

@ code933k Phiên bản nào vậy? Tôi sẽ không ngạc nhiên nếu hành vi đã thay đổi.
William Pursell

@WilliamPursell zsh 5.7.1
code933k
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.