সমান পদার্থের বাক্য গঠন কি না?


22

স্ক্রিপ্ট করার সময়, আমি সাধারণত আমার আইএফএসটি নীচের সিনট্যাক্স দিয়ে লিখি কারণ আমার পক্ষে বোঝা আরও সহজ যে এর পরে যা আসে তা সত্য নয়।

if [ ! "$1" = "$2" ]; then

অন্যরা বলেন যে নীচের পথটি আরও ভাল

if [ "$1" != "$2" ]; then

জিনিসটি যখন আমি জিজ্ঞাসা করি কেন এবং কেন কোনও মতপার্থক্য রয়েছে কিনা কারও কোনও উত্তর নেই বলে মনে হয়।

সুতরাং, দুটি সিনট্যাক্সের মধ্যে কোনও পার্থক্য রয়েছে? এর মধ্যে একটির কি অন্যের চেয়ে নিরাপদ? নাকি এটুকু পছন্দ / অভ্যাসের বিষয়?


9
প্রথম যদি আপনি অপারেটার পার্থক্য অগ্রাধিকার জানা প্রয়োজন !(x==y)থেকে (!x)==y
jimmij

@jimmij আপনি কি বলতে চান না যে, যখন একটি স্ট্রিং তুলনা এই if [ ! "$string" = "one" ]যদি না এর মান অনুবাদ $stringসমান one। এবং এটি if [ "$string" != "one"]অনুবাদ করে যদি মানটির $stringসাথে সমান হয় না one?
জিমি_এ

5
@ জিমি_এ আমার অর্থ যে এটি আপনার কীভাবে "অনুবাদ করে" তা জানতে হবে। অপারেটর একত্রিত করা ( !=সিনট্যাক্স) আরও স্পষ্ট।
jimmij

প্রিয় ঘনিষ্ঠ ভোটারগণ, স্টাফেনের উত্তরগুলি দেখায় যে আচরণের মধ্যে একটি উপাদানগত পার্থক্য রয়েছে, সঠিক উত্তরটি কোনওভাবেই মতামত ভিত্তিক নয়।
কেভিন

উত্তর:


35

প্রসাধনী / পছন্দ যুক্তিগুলির পাশাপাশি, একটি কারণ হতে পারে এমন আরও বাস্তবায়ন রয়েছে যেখানে [ ! "$a" = "$b" ]কোণার ক্ষেত্রে ব্যর্থ হয় [ "$a" != "$b" ]

উভয় ক্ষেত্রেই নিরাপদ হওয়া উচিত যদি বাস্তবায়নগুলি পসিক্স অ্যালগরিদম অনুসরণ করে তবে আজও (লিখিতভাবে 2018 সালের শুরুতে) এখনও কার্যকর রয়েছে যা ব্যর্থ হয়। উদাহরণস্বরূপ, এর সাথে a='(' b=')':

$ (a='(' b=')'; busybox test "$a" != "$b"; echo "$?")
0
$ (a='(' b=')'; busybox test ! "$a" = "$b"; echo "$?")
1

সঙ্গে dash0.5.9 পূর্বে সংস্করণ 0.5.8 পাওয়া যায় মত shউদাহরণস্বরূপ উবুন্টু 16,04 করুন:

$ a='(' b=')' dash -c '[ "$a" != "$b" ]; echo "$?"'
0
$ a='(' b=')' dash -c '[ ! "$a" = "$b" ]; echo "$?"'
1

(০.০.৯ এ স্থির হয়েছে, https://www.mail-archive.com/dash@vger.kernel.org/msg00911.html দেখুন )

এই বাস্তবায়নগুলি [ ! "(" = ")" ]যেমনটি [ ! "(" "text" ")" ]হয় [ ! "text" ]("টেক্সট" নাল স্ট্রিং কিনা তা পরীক্ষা করে) তবে পসিক্স এটিকে [ ! "x" = "y" ](সাম্যের জন্য "x" এবং "y" হিসাবে পরীক্ষা করার নির্দেশ দেয় )। এই প্রয়োগগুলি ব্যর্থ হয় কারণ তারা এই ক্ষেত্রে ভুল পরীক্ষা করে।

মনে রাখবেন যে আরও একটি ফর্ম রয়েছে:

! [ "$a" = "$b" ]

এটির জন্য একটি পসিক্স শেল প্রয়োজন (পুরানো বোর্ন শেলটি দিয়ে কাজ করবে না)।

নোট করুন যে বেশ কয়েকটি বাস্তবায়নের ক্ষেত্রেও [ "$a" = "$b" ](এবং [ "$a" != "$b" ]) সমস্যা রয়েছে এবং এখনও সোলারিস 10 (একটি বোর্ন শেল, পসিক্স শেলটি রয়েছে ) এর [বিল্টিনের মতোই রয়েছে । এজন্য আপনি যেমন জিনিস দেখতে পান:/bin/sh/usr/xpg4/bin/sh

[ "x$a" != "x$b" ]

স্ক্রিপ্টগুলিতে পুরানো সিস্টেমে পোর্টেবল হওয়ার চেষ্টা করছে।


সুতরাং অন্য কথায়, উভয় বাক্য গঠনই একই কাজ করে, যা কোনও পার্থক্য নয়, তবে ! "$a" = "b"তুলনাটি নির্দিষ্ট করার জন্য আপনি কীভাবে এটি লেখেন সে সম্পর্কে আপনার আরও যত্নবান হওয়া দরকার। আপনার উদাহরণ থেকে আমি বুঝতে পারি যে দ্বিতীয় কমান্ডটি প্রত্যাবর্তন করবে not zeroযা উপকারী বা ঝামেলা উভয়ই হতে পারে। আপনি যদি সেগুলি না মেলে প্রস্থান করতে চান তবে উপকার হতে পারে বা তুলনা ক্র্যাশ হয়েছে কিনা তা দেখতে আপনি যদি
ঝামেলা করছেন

2
@ জিমি_এ, না, বাস্তবায়নগুলি [ ! "$a" = "$b" ]কখন এবং কখন রয়েছে $aতা ব্যর্থ হয় , এটি দাবি করে যে তারা যখন অভিন্ন তখন একই রকম নয় , তবে সেই ক্ষেত্রে ভুল পরীক্ষা করে। ($b)()[
স্টাফেন চ্যাজেলাস

আহ্, আমি মনে করি এটি পেয়েছি। প্রথম এবং তৃতীয়টি শর্তটি সত্য কিনা তা যাচাই করার অর্থ, যখন দ্বিতীয়টি এবং চতুর্থ শর্তটি মিথ্যা কিনা। সুতরাং, প্রস্থান স্থিতি কোডগুলি পৃথক হচ্ছে। এটি মূলত বলছে, 1 এবং 4 ভেরিয়েবলগুলি পৃথক এবং 2 এবং 3 সমান নয়।
জিমি_এ

3
@ জিমি_এ, না আপনি বিন্দুটি পুরোপুরি মিস করেছেন। তাহলে এই বাস্তবায়নের POSIX অনুসৃত, তারপর সব স্থিতি কোডগুলি 0. হবে
ওয়াইল্ডকার্ড

আমি বুঝতে পেরেছি তা নিশ্চিত করার জন্য, এটি এটিকে সিদ্ধ করে দেয়: [ ! "$a" = "$b" ]কখনও কখনও বগি শেল বাস্তবায়নে ভুলভাবে পরিচালনা করা হয় (যা আমি মনে করি উত্তরের প্রথম বাক্যটি কমবেশি বিশ্রাম নিচ্ছে)।
মাইকেল বুড়

8

x != yকারণ সিনট্যাক্স উত্তম ! x == yত্রুটি প্রবণ - যা পৃথক ভাষা থেকে ভাষা থেকে অপারেটার পূর্ববর্তিতার জ্ঞান প্রয়োজন। সিনট্যাক্স ! x == yহিসেবে ব্যাখ্যা করা যেতে পারে !(x == y)বা (!x) == yঅগ্রাধিকার উপর নির্ভর করে, !বনাম =


উদাহরণস্বরূপ, c++অস্বীকৃতি ! তুলনা / রিলেশনাল অপারেটরের আগে আসে == , সুতরাং নিম্নলিখিত কোডটি:

#include<iostream>

using namespace std;

int main()
{
  int x=1, y=2;
  if(     x  != y   ) cout<<"true"<<endl; else cout<<"false"<<endl;
  if(  !  x  == y   ) cout<<"true"<<endl; else cout<<"false"<<endl;
  if(  !( x  == y ) ) cout<<"true"<<endl; else cout<<"false"<<endl;
  if(   (!x) == y   ) cout<<"true"<<endl; else cout<<"false"<<endl;
}

আয়

true
false
true
false

অনুরূপ আচরণ awkইউনিক্স বিশ্বে প্রায়শই ব্যবহৃত একটি সরঞ্জাম সহ - অন্যান্য অনেক ভাষায় দেখা যায় ।


অন্যদিকে, অপারেটরগুলির মাধ্যমে একত্রিত হয়ে x != yসু-প্রতিষ্ঠিত প্যাটার্ন হিসাবে কোনও বিভ্রান্তির কারণ হয় না। তদুপরি, প্রযুক্তিগতভাবে বলতে গেলে !=প্রায়শই দুটি হয় না, তবে কেবল একটি অপারেটর, তাই আলাদা তুলনা এবং তারপরে উপেক্ষার চেয়ে মূল্যায়ন করার জন্য এমনকি প্রান্তিক দ্রুত হওয়া উচিত। সুতরাং, যদিও উভয় বাক্য গঠন বাশে কাজ করে আমি অনুসরণ করার পরামর্শ দিই কারণ x != yকিছুটা স্ট্যান্ডার্ড লজিক অনুসরণ করে কোডটি পড়া এবং বজায় রাখা সহজ।


4

এই ধরণের জিনিসটি খুব মতামত-ভিত্তিক, কারণ "উত্তর" কোনও ব্যক্তির মস্তিষ্কের তারে সংঘটিত হওয়ার উপায়ের উপর নির্ভর করে। যদিও এটি সত্য যে শব্দার্থগতভাবে, NOT ( A == B )অভিন্ন (A != B ), তবে একজনের কাছে একজনের সাথে অন্যজন আরেকজনের কাছে পরিষ্কার হতে পারে। এটি প্রসঙ্গনির্ভর। উদাহরণস্বরূপ, যদি আমার একটি পতাকা সেট থাকে, তবে অন্যটির সিন্টেক্সের সাথে অর্থগুলি আরও স্পষ্ট হতে পারে:

if NOT ( fileHandleStatus == FS_OPEN )

উল্টোদিকে

if ( fileHandleStatus != FS_OPEN )

এমনকি পূর্বের নিয়োগের পরিবর্তে if ( FS_OPEN != fileHandleStatus )দুর্ঘটনাক্রমে টাইপিংয়ের স্বাচ্ছন্দ্যের ফলে এবং পরে সমতা পরীক্ষা (সি এর মতো) ...===
ডারবার্ট
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.