ইউনিক্সে লাইন দিয়ে দুটি পৃথক ফাইলের তুলনা কীভাবে?


13

file1:

123
234
345
456

File2:

123
234
343
758

প্রত্যাশিত আউটপুট: ফাইল 3:

TRUE
TRUE
FALSE
FALSE

সুতরাং কোডটির দুটি ফাইলের তুলনা করা উচিত এবং 'সত্য' মুদ্রণ করা উচিত যদি এটি মেলে অন্যথায় এটি নতুন ফাইলে 'ফলস' মুদ্রণ করে। কেউ দয়া করে এর জন্য সমাধান সরবরাহ করতে পারেন?


10
দুটি ফাইল অসম দৈর্ঘ্যের হলে কী হবে? এই সমস্যার সমাধানের কোন অংশটি নিয়ে আপনার সমস্যা হচ্ছে?
কুসালানন্দ

9
আপনি একবার দেখতে চাইবেন diff
পঙ্কি

2
এই পরিস্থিতিতে অন্যান্য দরকারী কমান্ড হয় comm। উভয় ফাইলের মিল রয়েছে বা এক বা অন্যের কাছে অনন্য রয়েছে এমন লাইনগুলি তালিকাবদ্ধ করা সহজ করে তোলে।
গিয়াকোমো আলজেটা

1
@ গিয়াকোমো অলজিটা এই জিনিসটির সাথে commএটির জন্য বাছাই করা ইনপুট দরকার। এ ছাড়াও যে প্রশ্নে উদাহরণ থেকে নেই সাজানো ইনপুট আছে, প্রশ্ন কখনো দাবি যে এই প্রকৃত তথ্য যে ব্যবহৃত হচ্ছে এবং ডেটা ক্রম সম্পর্কে কিছু বলছেন না।
কুসালানন্দ

2
αғsнιη এর nlকৌতুক সঙ্গে দরকারী commফাইল সাজানো-অন্তরীপ মনোরম জন্য।
গ্লেন জ্যাকম্যান

উত্তর:


56

প্রক্রিয়া বিকল্পগুলি সমর্থন করে এমন বা অন্য কোনও শেল diffহিসাবে কমান্ডটি নিম্নলিখিত হিসাবে ব্যবহার করুন বা আপনি এখানে প্রদর্শিত হিসাবে অনুকরণ করতে পারেন :bash<(...)

diff --new-line-format='FALSE'$'\n' \
     --old-line-format='' \
     --unchanged-line-format='TRUE'$'\n' \
<(nl file1) <(nl file2)

আউটপুট হবে:

TRUE
TRUE
FALSE
FALSE

--new-line-format='FALSE'$'\n, FALSEলাইনগুলি পৃথক হলে মুদ্রণ করুন এবং ফাইল 1 এর --old-line-format=''জন্য লাইন পৃথক থাকলে আমরা আউটপুট অক্ষম করে থাকি যা পুরানো ফাইলকে পৃথক কমান্ড হিসাবে পরিচিত (আমরা এগুলিও অদলবদল করতে পারতাম, যার অর্থ একটি FALSEঅপরকে মুদ্রণ করা উচিত।)

--unchanged-line-format='TRUE'$'\n', TRUEলাইনগুলি একই থাকলে মুদ্রণ করুন । $'\n'সি-শৈলী পলায়নের সিনট্যাক্স প্রতিটি লাইনে আউটপুট পরে একটি নতুন লাইন মুদ্রণ করতে ব্যবহৃত হয়।


24

ধরে নিচ্ছি ফাইলগুলিতে কোনও ট্যাব-অক্ষর নেই:

$ paste file1 file2 | awk -F '\t' '{ print ($1 == $2 ? "TRUE" : "FALSE") }'
TRUE
TRUE
FALSE
FALSE

এটি pasteউভয় কলামে দুটি ফাইলের বিষয়বস্তু সহ দুটি ট্যাব-সীমাবদ্ধ কলাম তৈরি করতে ব্যবহার করে। awkকমান্ড প্রতিটি লাইনে দুটি কলাম তুলনা এবং ছাপে TRUEযদি কলাম একই এবং অন্যথায় প্রিন্ট হয় FALSE


10

ধরে নিচ্ছি উভয় ফাইলের একই সংখ্যক লাইন রয়েছে:

awk '{getline f2 < "file2"; print f2 == $0 ? "TRUE" : "FALSE"}' file1

এটি একটি সাংখ্যিক তুলনা করছে যদি তুলনা করার স্ট্রিংগুলি সংখ্যা এবং অন্যথায় বর্ণিক হয়। উদাহরণস্বরূপ, 100এবং 1.0e2অভিন্ন হিসাবে বিবেচিত হবে। যে f2"" == $0কোনও ক্ষেত্রে একটি লেজিকাল তুলনা জোর করতে পরিবর্তন করুন ।

awkবাস্তবায়নের উপর নির্ভর করে লেক্সিকাল তুলনাটি এমনভাবে করা হবে যেন ব্যবহার করে memcmp()(বাইট-টু-বাইট তুলনা) বা যেমন ব্যবহার করে strcoll()(দুটি স্ট্রিং লোকালের কোলেশন ক্রমে একই সাজান কিনা)। এটি কিছু লোকেলগুলিতে পার্থক্য আনতে পারে যেখানে কয়েকটি অক্ষরের জন্য অর্ডারটি সঠিকভাবে সংজ্ঞায়িত করা হয় না, আপনার নমুনার মতো দশমিক ডিজিটের ইনপুটগুলিতে নয়।


7

পাইথন ঘ

with open('file1') as file1, open('file2') as file2:
    for line1, line2 in zip(file1, file2):
        print(line1 == line2)

আউটপুট:

True
True
False
False

আপনার যদি প্রয়োজন হয় TRUEএবং FALSEবড় হাতের অক্ষরে থাকে তবে মুদ্রিত লাইনটি এর মধ্যে একটির সাথে প্রতিস্থাপন করুন:

print(str(line1 == line2).upper())
print('TRUE' if line1 == line2 else 'FALSE')

2
পাইথন 2 এ, import itertoolsপ্রথমে একটি করুন এবং তার itertools.izipপরিবর্তে ব্যবহার করুন zip। অন্যথায় এটি দুটি ফাইল মেমোরিতে পড়বে, সম্ভবত খুব বেশি মেমরি ব্যবহার করা হবে।
pts

4

ইন bash, প্রতিটি ফাইল থেকে একটি whileলুপে পড়া, পড়ার লাইনগুলি এবং মুদ্রণের তুলনা TRUEবা FALSEযথাযথভাবে:

while IFS= read -r -u3 line1; IFS= read -r -u4 line2; do
    [[ $line1 == $line2 ]] && echo TRUE || echo FALSE
done 3<file1 4<file2

readফাইল বর্ণনাকারী থেকে যথাক্রমে 3 এবং 4 পাঠানোর জন্য দুটি কল । লুপগুলিতে দুটি ইনপুট পুনঃনির্দেশ সহ ফাইলগুলি এগুলিতে পুনঃনির্দেশিত হয়।


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