সেড: কীভাবে লাইনটি প্রতিস্থাপন করবেন বা যদি পাওয়া না যায় তবে ফাইলের শেষের দিকে সংযোজন করবেন?


34

একটি একক ইনপুট ফাইলের সাথে কেবল মন্তব্য রয়েছে (# দিয়ে শুরু) এবং VARIABLE = মান লাইন, যদি পাওয়া যায় তবে একক ভেরিয়েবলের জন্য কোনও মান প্রতিস্থাপন করা সম্ভব এবং অন্যথায়, খুঁজে পাওয়া না গেলে ফাইলটির শেষে জুটি যুক্ত করা যায়?

আমার বর্তমান পদ্ধতিটি এটি প্রথম পাসে মুছে ফেলার মাধ্যমে কাজ করে, তারপরে এটি দ্বিতীয় পাসে ফাইলের শেষের দিকে যুক্ত করে, তবে এই পদ্ধতিটি লাইন ক্রমটি অস্থির করে তোলে (এবং দুটি পৃথক কমান্ডও রয়েছে):

sed -r "/^FOOBAR=.*$/d"      -i samefile &&
sed -r "$ a\FOOBAR=newvalue" -i samefile

এটি করার জন্য যেভাবেই আছে? লাইন অর্ডার, একক সেড লাইনে? যদি অন্য কোনও ইউটিলিটি (অ্যাডাব্লু, ...) এটি করে থাকে তবে আমি সেডের উপর দিয়ে যাব।

উত্তর:


29

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

sed '/^FOOBAR=/{h;s/=.*/=newvalue/};${x;/^$/{s//FOOBAR=newvalue/;H};x}' infile

উপরে gnu sedসিনট্যাক্স। সুবহ:

sed '/^FOOBAR=/{
h
s/=.*/=newvalue/
}
${
x
/^$/{
s//FOOBAR=newvalue/
H
}
x
}' infile

1
newvalueভেরিয়েবলে সঞ্চিত থাকলে এটিকে কেমন দেখাচ্ছে ?
ব্যবহারকারী 1810087

sed "/^${varName}=/{h;s/=.*/=${varValue}/};\${x;/^$/{s//${varName}=${varValue}/;H};x}" ${VARFILE}ভেরিয়েবল, ডাবল কোট সহ ভেরিয়েবল প্রতিস্থাপনের অনুমতি দিতে এবং $এই মুহুর্তে প্রতিস্থাপন নয় এমন একটি পলায়ন , অতিরিক্ত হিসাবে যদি আপনি মান সংরক্ষণ করেন $$varName:sed "/^${varName}=/{h;s/=.*/=${!varName}/};\${x;/^$/{s//${varName}=${!varName}/;H};x}" ${VARFILE}
ডার্কমুককে

1
এই সমাধানটি 'সরল' নয় ol কিন্তু এটি কাজ করে. সেড ম্যান পেজগুলি সন্ধানের পক্ষে সহজ জিনিস নয়, আপনি যদি অভিব্যক্তিটির প্রতিটি বিভাগের প্রভাবটি বিস্তারিতভাবে বর্ণনা করতে পারেন তবে তা সহায়ক হবে :)
ইউজার2066480

18

এটি সম্ভবত সংক্ষিপ্ত করা যেতে পারে। এটি একটি সিড কমান্ড নয় এবং এটি গ্রেপ ব্যবহার করে তবে এটি মূলত আপনি যা চাইছেন তা মনে হয়। এটি একটি একক লাইন, এবং এটি স্থানটিতে ফাইল সম্পাদনা করে (কোনও টেম্প ফাইল নেই)।

grep -q "^FOOBAR=" file && sed "s/^FOOBAR=.*/FOOBAR=newvalue/" -i file || 
    sed "$ a\FOOBAR=newvalue" -i file

13

এখানে একটি সহজ sedপদ্ধতির উপায় হিসাবে আমি কাজ করতে sed hold spaceসহজ মনে করি না easy আপনি যদি স্বাচ্ছন্দ্য বোধ করেন hold spaceতবে don_crissti পদ্ধতির ব্যবহারটি বিদ্যমান লাইন থেকে যে কোনও কিছু সংরক্ষণের জন্য অতিরিক্ত সুযোগ দেয় তবে এটি সাধারণত খুব বিরল।

এই পদ্ধতির ক্ষেত্রে, আপনি কেবল যে রেখাটি ফেলে দিতে চান তা ছাড়াই এবং তারপরে শেষে প্রতিস্থাপনটি যুক্ত করুন print

sed -n -e '/^FOOBAR=/!p' -e '$aFOOBAR=newvalue' infile

1
এই সংস্করণটি খুব ভাল তবে আপনি যদি এমন কোনও ফাইল আপডেট করার পরিকল্পনা করেন যার বিদ্যমান বা পুরানো মান থাকতে পারে।
guillem

3

অন্যান্য উত্তরের উপর ভিত্তি করে, আপনি যা করতে চান তা যদি ভেরিয়েবলের ফাইলে উপস্থিত থাকে এবং ভেরিয়েবলের মানটি প্রতিস্থাপন করা হয় এবং এটি যদি আপনার পোস্টের sedআদেশগুলি না করে (তবে এটি আপনার পোষ্ট কমান্ডগুলি করে না) তবে আপনি এটি পরিবর্তন করতে পারেন end এটি চেষ্টা করতে পারে:

perl -ne '$c=1 if s/^FOOBAR=.*$/FOOBAR=newvalue/;  
             print; 
             END{print "FOBAR=newvalue" unless $c==1}' file > tmpfile && 
mv tmpfile file

1

এটি "অ্যাড প্লেস এডিটিং" স্বয়ংক্রিয় না হলেও এটি জঞ্জাল থেকে কিছুটা সহজ easier

awk -v varname="FOOBAR" -v newval="newvalue" '
    BEGIN {FS = OFS = "="}
    $1 == varname {$2 = newval; found = 1}
    {print}
    END {if (! found) {print varname, newval}}
' file > tempfile &&
mv tempfile file

1

কেবলমাত্র ব্যবহার grepএবং echoএকটি খালি রেকর্ড তৈরি করতে:

grep -q '^FOOBAR=' somefile || echo 'FOOBAR=VALUE' >> somefile
sed -i 's/FOOBAR=.*$/FOOBAR=VALUE/' somefile 

প্রতিটি লাইন ত্রুটি কোড শূন্যের সাথে পালিয়ে যায়।


অতিরিক্ত কমান্ড যুক্ত করার সময় আপনি লাইন ক্রম হারাবেন এবং grepএবংecho
ব্লাকব্যাট

প্রকৃতপক্ষে যদি আপনি ফাইলের শেষে নতুন আইটেমগুলি সন্নিবেশ করেন তবে আপনি যদি কোনও পুরানো মান প্রতিস্থাপন করেন তবে ক্রম বজায় রাখুন।
MUY বেলজিয়াম

0

প্রকৃতপক্ষে নিম্নলিখিতগুলির সাথে কাজ করে: sed -i '/^FOOBAR=/{h;s/=.*/=newvalue/};${x;/^$/{s//FOOBAR=newvalue/;H};x}' infile উত্তরে চয়নসেন -i অনুপস্থিত।


3
এটি সত্যই একটি মন্তব্য এবং মূল প্রশ্নের উত্তর নয় । কোনও লেখকের কাছ থেকে সমালোচনা বা স্পষ্টতার জন্য অনুরোধ জানাতে, তাদের পোস্টের নীচে একটি মন্তব্য দিন - আপনি সর্বদা আপনার নিজের পোস্টে মন্তব্য করতে পারেন, এবং আপনার যথেষ্ট সুনামের পরে আপনি কোনও পোস্টে মন্তব্য করতে সক্ষম হবেন । দয়া করে পড়ুন মন্তব্য করার জন্য আমার কেন 50 খ্যাতি দরকার? এর পরিবর্তে আমি কী করতে পারি?
DavidPostill

-1

পার্ল দিয়ে এই কাজটি করার জন্য এবং এটি আমার জন্য ভাল কাজ করে:

grep ^FOOBAR= my.file && perl -i -ple "s/^FOOBAR=.+/FOOBAR=newvalue/g" my.file || echo FOOBAR=newvalue >> my.file

2
এই উত্তরটি অনেক উপায়ে খারাপ ! grepএবং echoএবং perlপরিবর্তে সবকিছু করছেন perl? এছাড়াও, আপনি ( >> my.file) পাঠ করছেন এমন কোনও ফাইলে ( ) লিখছেন grep my.file?
ভ্লাদার
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.