স্পেস এবং ওয়াইল্ডকার্ডযুক্ত পাথের সাথে স্ট্রিং সহ বাশ স্ক্রিপ্ট ত্রুটি


25

ব্যাসের স্ক্রিপ্টিংয়ের মূল কথাটি পেতে আমার সমস্যা হচ্ছে। আমার এখন পর্যন্ত যা আছে তা এখানে:

#!/bin/bash
FILES="/home/john/my directory/*.txt"

for f in "${FILES}"
do
  echo "${f}"
done

আমি যা করতে চাই তা হ'ল সমস্ত .txtফাইলগুলিকে একটি forলুপে তালিকাবদ্ধ করা যাতে আমি তাদের সাথে স্টাফ করতে পারি। তবে কেবলমাত্র স্থানটিতে my directoryএবং তারকাটি *.txtখুব ভাল খেলছে না। আমি এটি ভেরিয়েবল নামের কোঁকড়ানো ধনুর্বন্ধনী সঙ্গে এবং ছাড়াই ডাবল উদ্ধৃতি সহ এবং ব্যবহার করার চেষ্টা করেছি এবং এখনও সমস্ত .txtফাইল মুদ্রণ করতে পারি না ।

এটি একটি খুব বেসিক জিনিস, তবে আমি এখনও লড়াই করছি কারণ আমি ক্লান্ত এবং সরাসরি চিন্তা করতে পারি না।

আমি কি ভুল করছি?

আমার ফাইলগুলিতে কোনও জায়গা বা একটি নক্ষত্রপুঞ্জ না থাকলে আমি উপরের স্ক্রিপ্টটি সফলভাবে প্রয়োগ করতে সক্ষম হয়েছি ... এটি কাজ করতে আমাকে ডাবল কোটস এবং ব্রেস ব্যবহার বা ব্যবহার না করে পরীক্ষা করতে হয়েছিল। তবে যে মুহুর্তে আমার উভয় স্থান এবং একটি তারকাচিহ্ন রয়েছে, এটি সমস্ত কিছু গোলমাল করে।

উত্তর:


33

কোটের ভিতরে, *ফাইলগুলির তালিকায় প্রসারিত হবে না। এই জাতীয় ওয়াইল্ডকার্ড সফলভাবে ব্যবহার করতে, এটি অবশ্যই উদ্ধৃতিগুলির বাইরে থাকতে হবে।

এমনকি ওয়াইল্ডকার্ডটি প্রসারিত না হলেও, এক্সপ্রেশনটির "${FILES}"ফলস্বরূপ ফাইলগুলির একটি তালিকা নয়, একক স্ট্রিংয়ের ফলস্বরূপ।

একটি পদ্ধতির যে কাজ করবে:

#!/bin/bash
DIR="/home/john/my directory/"
for f in "$DIR"/*.txt
do
  echo "${f}"
done

উপরের অংশে, ফাঁকা জায়গা বা অন্যান্য কঠিন অক্ষরের ফাইলের নামগুলি সঠিকভাবে পরিচালনা করা হবে।

আরও উন্নত পদ্ধতি ব্যাশ অ্যারে ব্যবহার করতে পারে:

#!/bin/bash
FILES=("/home/john/my directory/"*.txt)
for f in "${FILES[@]}"
do
  echo "${f}"
done

এই ক্ষেত্রে, FILESফাইল নামের একটি অ্যারে হয়। সংজ্ঞাটি ঘিরে পেরেনগুলি এটিকে একটি অ্যারে করে তোলে। মনে রাখবেন যে *উদ্ধৃতিগুলির বাইরে। কনস্ট্রাক্ট "${FILES[@]}"একটি বিশেষ কেস: এটি স্ট্রিংগুলির তালিকায় প্রসারিত হবে যেখানে প্রতিটি স্ট্রিং ফাইলের একটির নাম। ফাঁকা জায়গা বা অন্যান্য কঠিন অক্ষরের ফাইলের নামগুলি সঠিকভাবে পরিচালনা করা হবে।


1
দুর্দান্ত যে কাজ করেছে
জন

এটি লক্ষণীয় যে আপনি যদি ফাংশনগুলির মাধ্যমে এই জাতীয় পথগুলি অতিক্রম করে থাকেন তবে আপনাকে অবশ্যই বৃহত্তর স্ট্রিংয়ের অংশ হিসাবে এটি যুক্ত করে for f in "$DIR"/*.txtfor f in "$DIR/*.txt"
তুলনামূলক

7

জন ১০৪৪-এর দেখানো অ্যারেগুলি ব্যবহার করে আরও অনেক কিছু বোঝা যায়, এখানে, আপনি বিভক্ত + গ্লোব অপারেটরটিও ব্যবহার করতে পারেন (একটি স্কেলার ভেরিয়েবল অব্যক্ত রেখে)।

যেহেতু আপনি কেবল সেই অপারেটরের গ্লোব অংশ চান তাই আপনার বিভক্ত অংশটি অক্ষম করতে হবে :

#! /bin/sh -
# that also works in any sh, so you don't even need to have or use bash

file_pattern="/home/john/my directory/*.txt"
# all uppercase variables should be reserved for environment variables

IFS='' # disable splitting

for f in $file_pattern # here we're not quoting the variable so
                       # we're invoking the split+glob operator.
do
  printf '%s\n' "$f" # avoid the non-reliable, non-portable "echo"
done

0

আপনি যা করতে পারেন তা হল উদ্ধৃতিগুলির বাইরে কেবল ওয়াইল্ডকার্ডের অক্ষরগুলি রেখে যাওয়া।
ভালো কিছু:
"স্পেস দিয়ে ফাইল" একটি জন্য * "। পাঠ্য"
না
প্রসেসিং
সম্পন্ন
ওয়াইল্ডকার্ড নিজেদের জায়গা প্রসারিত করবে, তাহলে আপনি টি লাইন পদ্ধতির প্রতি একটি ফাইল ব্যবহার, ব্যবহার ম মত একটি তালিকা জেনারেট করতে -l প্রয়োজন হবে প্রতিটি ফাইল পেতে ফাইল এবং ব্যাশ রিড ব্যবহার করুন।


-1

আপনি যখন ফাইলগুলির সেট প্রসেস করতে চান, আপনি বিবেচনা করবেন, তাদের নামে স্থান থাকতে পারে বা অন্য স্কেপ কোড থাকবে, সুতরাং আপনার প্রক্রিয়া শুরু করার আগে যেমন for loopবা এটিকে find commandসেট করুন IFS bash env variable:

IFS=$(echo -en "\n\b")
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.