বাশগুলিতে ডাবল উদ্ধৃতি চিহ্নগুলি কীভাবে মিলিত হয় (যুক্ত)?


15

আমি ব্যবহার করছি GNU bash 4.3.48। নিম্নলিখিত দুটি কমান্ড বিবেচনা করুন যা কেবলমাত্র একক ডলারের চিহ্ন দ্বারা পৃথক।

আদেশ 1:

echo "(echo " * ")"

কমান্ড 2:

echo "$(echo " * ")"

তাদের আউটপুট যথাক্রমে হয়

(echo  test.txt ppcg.sh )

এবং

 * 

স্পষ্টতই প্রথম ক্ষেত্রে কেস *গ্লোবড হয়, যার অর্থ প্রথম উদ্ধৃতি চিহ্নটি দ্বিতীয়টির সাথে একটি জুটি তৈরি করে, এবং তৃতীয় এবং চতুর্থটি আরেকটি জুটি তৈরি করে।

দ্বিতীয় ক্ষেত্রে এটি *গ্লোবড হয় না, এবং আউটপুটে ঠিক দুটি অতিরিক্ত স্থান থাকে, একটি নক্ষত্রের আগে এবং তার পরে, যার অর্থ দ্বিতীয় উদ্ধৃতি চিহ্নটি তৃতীয়টির সাথে যায় এবং প্রথমটি চতুর্থের সাথে যায়।

$()নির্মাণ ব্যতীত অন্য কোনও মামলা রয়েছে যে উদ্ধৃতি চিহ্নগুলি পরেরটির সাথে মেলে না, তবে তার পরিবর্তে বাসা বাঁধে? এই আচরণটি কি ভালভাবে নথিভুক্ত করা হয়েছে এবং যদি হ্যাঁ, তবে আমি সংশ্লিষ্ট নথিটি কোথায় পাব?



আবারও, উল এসই-তে সিনট্যাক্স হাইলাইটটি ভুল এবং বিভ্রান্তিমূলক, যদিও প্রিটিফাইফাই জেএসকেই দোষ দেওয়া যায়।
ওয়েজুন চাউ

উত্তর:


14

নীড় নির্মাণের যে কোনও কাঠামো স্ট্রিংগুলির অভ্যন্তরে বিভক্ত হতে পারে তার মধ্যে আরও স্ট্রিং থাকতে পারে: এগুলি একটি নতুন স্ক্রিপ্টের মতো পার্স করা হয়, সমাপ্তি চিহ্নিতকারী পর্যন্ত, এবং এমনকি একাধিক স্তর গভীরভাবে বাসা বাঁধতে পারে। এগুলির মধ্যে সমস্ত বার একটি দিয়ে শুরু হয় $। এগুলি সবই বাশ ম্যানুয়াল এবং পসিক্স শেল কমান্ড ভাষার স্পেসিফিকেশনের সংমিশ্রণে নথিভুক্ত করা হয়েছে।

এই নির্মাণগুলির কয়েকটি মামলা রয়েছে:

  • কমান্ড প্রতিস্থাপন$( ... ) , যেমন আপনি খুঁজে পেয়েছেন। পসিএক্স এই আচরণটি নির্দিষ্ট করে :

    সঙ্গে $(command)ফর্ম, ম্যাচিং সমাপনী প্রথম বন্ধনী খোলা প্রথম বন্ধনী নিম্নলিখিত সমস্ত অক্ষর কমান্ড গঠন করে। যে কোনও বৈধ শেল স্ক্রিপ্ট কমান্ডের জন্য ব্যবহার করা যেতে পারে ...

    উদ্ধৃতিগুলি বৈধ শেল স্ক্রিপ্টগুলির একটি অংশ, তাই তাদের তাদের সাধারণ অর্থ সহ অনুমোদিত।

  • কমান্ড বিকল্প ব্যবহার `করে।
  • উন্নত পরামিতি প্রতিস্থাপনের উদাহরণগুলির${parameter:-word} "শব্দ" উপাদান । "শব্দ" এর সংজ্ঞাটি হ'ল :

    শেল দ্বারা ইউনিট হিসাবে বিবেচিত অক্ষরের একটি ক্রম

    - এতে উদ্ধৃত পাঠ্য এবং এমনকি মিক্সড কোটসও অন্তর্ভুক্ত রয়েছে a"b"c'd'e- যদিও সম্প্রসারণের আসল আচরণটি এর চেয়ে কিছুটা উদার এবং উদাহরণস্বরূপ ${x:-hello world}এটিও কার্যকর।

  • পাটিগণিত সম্প্রসারণ সঙ্গে $(( ... )), যদিও এটি মূলত অনর্থক সেখানে (কিন্তু আপনি নীড় কমান্ড প্রতিস্থাপন বা পরিবর্তনশীল প্রসারণও, অত্যধিক করুন, এবং তারপর কোট থাকতে পারে থেকে কার্যকররূপে ঐ ভিতরে)। পসিক্স জানিয়েছে যে :

    অভিব্যক্তিটি এমনভাবে ধরা হবে যেন এটি ডাবল-কোটে থাকে, ব্যতীত এক্সপ্রেশনটির ভিতরে একটি ডাবল-কোট বিশেষভাবে বিবেচনা করা হয় না। শেলটি প্যারামিটার সম্প্রসারণ, কমান্ড প্রতিস্থাপন এবং উদ্ধৃতি অপসারণের জন্য এক্সপ্রেশনটিতে সমস্ত টোকেন প্রসারিত করবে।

    সুতরাং এই আচরণের স্পষ্টতই প্রয়োজনীয়। এর অর্থ echo "abc $((4 "*" 5))"গাণিতিকের চেয়ে পাটিগণিত হয়।

    দ্রষ্টব্য যে পুরাতন শৈলীর $[ ... ]পাটিগণিতের বিস্তৃতি একইরূপে চিকিত্সা করা হয় না : উদ্ধৃতিগুলি প্রদর্শিত হয় যদি তা প্রদর্শিত হয় তবে তা বর্ধিত হয় বা না হয় তা নির্বিশেষে es এই ফর্মটি আর কোনওভাবেই নথিভুক্ত করা হয়নি এবং এটি যেভাবেই হোক ব্যবহার করার জন্য নয়।

  • এর সাথে লোকেল-নির্দিষ্ট অনুবাদ$"..." , যা "মূল উপাদান হিসাবে ব্যবহৃত হয়। $"একটি একক হিসাবে বিবেচনা করা হয়।

নীড়ের আরও একটি মামলা রয়েছে যা আপনি আশা করতে পারেন না, উদ্ধৃতি জড়িত না, যা ব্রেস প্রসারণ সহ : {a,b{c,d},e}"বিসি বিডি ই" তে প্রসারিত। ${x:-a{b,c}d}না না নীড় তবে; এটি " a{b,c" এর পরে " " প্রদানের পরে একটি পরামিতি বিকল্প হিসাবে বিবেচিত হয় d}। এটি নথিভুক্তও রয়েছে :

যখন ধনুর্বন্ধনী ব্যবহার করা হয়, ম্যাচিং এন্ডেজ ব্রেস হ'ল প্রথম '}' ব্যাকস্ল্যাশ বা উদ্ধৃত স্ট্রিংয়ের মাধ্যমে এড়ানো যায় না এবং এম্বেডেড পাটিগণিতের বিস্তৃতি, কমান্ড প্রতিস্থাপন বা প্যারামিটার বিস্তারের মধ্যে নয় not


একটি সাধারণ নিয়ম হিসাবে, সমস্ত সীমিত নির্মানকারীরা তাদের দেহকে পার্শ্ববর্তী প্রসঙ্গে স্বাধীনভাবে পার্স করে (এবং ব্যতিক্রমগুলি বাগ হিসাবে গণ্য হয় )। সংক্ষেপে, $(কমান্ড-প্রতিস্থাপন কোডটি দেখে পার্সারকে কেবল শরীর থেকে যা তা করতে পারে তা গ্রাস করতে বলে, যদিও এটি একটি নতুন প্রোগ্রাম, এবং তারপরে সাব-পার্সার চালিত হওয়ার পরে প্রত্যাশিত সমাপ্তি চিহ্নিতকারী (একটি অব্যক্ত )বা ))বা }) প্রদর্শিত হবে কিনা তা পরীক্ষা করে দেখুন জিনিস বাইরে এটি গ্রাস করতে পারে।

যদি আপনি কোনও পুনরাবৃত্ত-বংশদ্ভূত পার্সারের কার্যকারিতা সম্পর্কে চিন্তা করেন , তবে এটি বেস কেসে কেবল একটি সাধারণ পুনরাবৃত্তি। অন্য উপায়ের চেয়ে এটি করা সহজতর, একবার আপনি মোটেও স্ট্রিং ইন্টারপোলেশন পেয়ে যান। অন্তর্নিহিত পার্সিং কৌশল নির্বিশেষে, এই নির্মাণগুলিকে সমর্থনকারী শেলগুলি একই ফল দেয়।

আপনি এই নির্মাণগুলির মাধ্যমে আপনার মতো গভীরভাবে উদ্ধৃতি দিতে পারেন এবং এটি প্রত্যাশার মতো কাজ করবে work মাঝখানে কোট দেখে কোথাও বিভ্রান্ত হবে না; পরিবর্তে, এটি অভ্যন্তর প্রসঙ্গে একটি নতুন উদ্ধৃত স্ট্রিংয়ের সূচনা হবে।


ধন্যবাদ। ইন "blah/blah\n$(cat "${tmpdir}/${filename}.jpdf")", দ্বিতীয় ডাবল উদ্ধৃতিটি কেন প্রথম ডাবল উদ্ধৃতিটির সমাপ্তি নয় (আপনার জবাবটিতে সিনট্যাক্স হাইলাইট করে দেখানো হয়েছে), কিন্তু ভিতরে একটি স্ট্রিংয়ের শুরু $(...)? এটি কি কারণ বাশের পার্সারটি ডাউন-আপের পরিবর্তে উপরে-ডাউন?
টিম

2
হ্যান্ডলিংয়ে "${var-"foo"}"( echo "${-+"*"}"যেমন echo *বোর্ন বা কর্ন শেলের মতোই উদাহরণস্বরূপ) অনেকগুলি ভিন্নতা রয়েছে এবং স্ট্যান্ডার্ডের পরবর্তী সংস্করণে আচরণটি স্পষ্টভাবে অনির্দিষ্ট করা হবেমেইল -আরচাইভ.আওস্টিন
স্টাফেন

3

সম্ভবত printf(এর পরিবর্তে echo) দুটি উদাহরণের সাহায্যে সহায়তা করবে:

$ printf '<%s> ' "(echo " * ")"; echo
<(echo > <test.txt> <ppcg.sh> <file1> <file2> <file3> <)>

এটি (echo (পিছনের স্থান সহ প্রথম শব্দ), কিছু ফাইল এবং সমাপ্ত শব্দটি মুদ্রণ করে )
প্রথম বন্ধনী হ'ল উদ্ধৃত স্ট্রিংয়ের একটি অংশ (echo 
তারকাচিহ্ন (এখন দুটি উদ্ধৃতি জোড়া লাগানো হিসাবে উদ্ধৃত) মিলে যাওয়া ফাইলগুলির তালিকায় গ্লোব হিসাবে প্রসারিত হয়েছে।
এবং তারপরে, ক্লোজিং বন্ধনী।

যাইহোক, আপনার দ্বিতীয় কমান্ড নিম্নলিখিত হিসাবে কাজ করে:

$ printf '<%s> ' "$(echo " * ")" ; echo
< * >

$কমান্ড প্রতিকল্পন শুরু হয়। এটি উদ্ধৃতিটি নতুন করে শুরু করে।
তারকাচিহ্নটি উদ্ধৃত হয় " * "এবং এটি হ'ল কমান্ড (এখানে এটি একটি আদেশ এবং একটি উদ্ধৃত স্ট্রিং নয়) echoফলাফলগুলি p শেষ পর্যন্ত, printfপুনরায় ফর্ম্যাট করে *এবং এটি প্রিন্ট করে < * >

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.