ইউনিকোড পাঠ্য প্রক্রিয়াকরণের দুটি স্তর রয়েছে are প্রথমটি হ'ল "আমি কীভাবে এটি ইনপুট করতে পারি এবং তথ্য হারানো ছাড়া এটি আউটপুট করতে পারি"। দ্বিতীয়টি হ'ল "স্থানীয় ভাষার সম্মেলন অনুসারে আমি কীভাবে পাঠ্যের সাথে আচরণ করব"।
tchrist এর পোস্ট উভয়ই কভার, কিন্তু দ্বিতীয় অংশটি যেখানে তার পোস্টে লেখা 99% এসেছে। বেশিরভাগ প্রোগ্রামগুলি আই / ওকেও সঠিকভাবে পরিচালনা করে না, সুতরাং আপনার এমনকি স্বাভাবিককরণ এবং কোলেশন সম্পর্কে চিন্তা করা শুরু করার আগে এটি বুঝতে গুরুত্বপূর্ণ।
এই পোস্টটি প্রথম সমস্যাটি সমাধান করার লক্ষ্য নিয়েছে
আপনি যখন পার্লে ডেটা পড়েন তখন এটিকে কী এনকোডিং করা হয় তা বিবেচ্য নয়। এটি কিছু স্মৃতি বরাদ্দ করে এবং বাইটগুলি দূরে সরিয়ে দেয়। যদি আপনি বলেন print $str
, এটি কেবল আপনার টার্মিনালে to বাইটগুলি অন্ধ করে দেয়, যা সম্ভবত এটিতে লেখা সমস্ত কিছুই ইউটিএফ -8 হিসাবে ধরে নিবে এবং আপনার পাঠ্যটি প্রদর্শিত হবে।
অবিশ্বাস্য।
ব্যতীত, তা নয়। আপনি যদি ডেটাটিকে পাঠ্য হিসাবে বিবেচনা করার চেষ্টা করেন তবে দেখবেন কিছুটা খারাপ হচ্ছে Bad length
পার্ল আপনার স্ট্রিং সম্পর্কে কী চিন্তা করে এবং আপনার স্ট্রিং সম্পর্কে আপনি কী ভাবেন সে সম্পর্কে এটি দেখার দরকার নেই । ওয়ান-লাইনারের মতো লিখুন: perl -E 'while(<>){ chomp; say length }'
টাইপ করুন 文字化け
এবং আপনি 12 পেয়ে যাবেন ... সঠিক উত্তর নয়, 4।
এর কারণ পার্ল ধরে নেয় যে আপনার স্ট্রিংটি পাঠ্য নয়। আপনাকে এটি বলতে হবে যে এটি সঠিক উত্তর দেওয়ার আগে এটি পাঠ্য।
এটি যথেষ্ট সহজ; এনকোড মডিউলটির এটি করার জন্য ফাংশন রয়েছে। জেনেরিক এন্ট্রি পয়েন্টটি Encode::decode
(বা use Encode qw(decode)
অবশ্যই)। এই ফাংশনটি বাইরের বিশ্ব থেকে কিছু স্ট্রিং নেয় (যা আমরা "অক্টেটস" বলি, "8-বিট বাইট" বলার অভিনব উপায়) এবং এটিকে এমন কিছু পাঠ্যে পরিণত করে যা পার্ল বুঝতে পারবে। প্রথম যুক্তি হ'ল "ইউটিএফ -8" বা "এএসসিআইআই" বা "ইইউসি-জেপি" এর মতো একটি অক্ষর এনকোডিংয়ের নাম। দ্বিতীয় যুক্তিটি স্ট্রিং। ফেরতের মানটি হ'ল পাঠ্যযুক্ত পার্ল স্কেলার ala
(এছাড়াও রয়েছে Encode::decode_utf8
, যা এনকোডিংয়ের জন্য ইউটিএফ -8 অনুমান করে))
যদি আমরা আমাদের ওয়ান-লাইনটিকে আবার লিখি:
perl -MEncode=decode -E 'while(<>){ chomp; say length decode("UTF-8", $_) }'
আমরা 文字 化 け টাইপ করি এবং ফলাফল হিসাবে "4" পাই। সাফল্য।
এটি ঠিক এখনই, পার্লের ইউনিকোডের 99% সমস্যার সমাধান।
মূলটি হ'ল যখনই কোনও প্রোগ্রাম আপনার প্রোগ্রামে আসে তখন আপনাকে অবশ্যই এটি ডিকোড করতে হবে। ইন্টারনেট অক্ষর স্থানান্তর করতে পারে না। ফাইলগুলি অক্ষর সংরক্ষণ করতে পারে না। আপনার ডাটাবেসে কোনও অক্ষর নেই। এখানে কেবলমাত্র অক্টেট রয়েছে এবং আপনি পার্টের অক্ষর হিসাবে অক্টেটগুলি আচরণ করতে পারবেন না। আপনাকে অবশ্যই এনকোডযুক্ত অক্টেটগুলি এনকোড মডিউল দিয়ে পার্ল অক্ষরে ডিকোড করতে হবে।
সমস্যার অর্ধেকটি আপনার প্রোগ্রামের বাইরে ডেটা পেয়ে যাচ্ছে। এটি সহজ; আপনি শুধু বলতে use Encode qw(encode)
ঠিক কি আপনার ডেটা এনকোডিং (টার্মিনাল যে হল UTF-8, হল UTF-16 Windows এ ফাইলের জন্য, ইত্যাদি বুঝতে হল UTF-8) মধ্যে হতে হবে, এবং তারপর আউটপুট ফলাফলের encode($encoding, $data)
শুধু outputting পরিবর্তে $data
।
এই অপারেশনটি পার্লের চরিত্রগুলিকে রূপান্তর করে যা আপনার প্রোগ্রামটি যা পরিচালনা করে তা বাইরের বিশ্বের দ্বারা ব্যবহার করা যেতে পারে oc এটি কেবলমাত্র আমরা ইন্টারনেটে বা আমাদের টার্মিনালগুলিতে অক্ষরগুলি প্রেরণ করতে পারলে এটি অনেক সহজ হবে, তবে আমরা এটি করতে পারি না: কেবলমাত্র অক্টেটস। সুতরাং আমাদের অক্ষরকে অষ্টেটে রূপান্তর করতে হবে, অন্যথায় ফলাফলগুলি সংজ্ঞায়িত।
সংক্ষিপ্তসার হিসাবে: সমস্ত আউটপুট এনকোড করুন এবং সমস্ত ইনপুট ডিকোড করুন।
এখন আমরা তিনটি বিষয় নিয়ে কথা বলব যা এটিকে সামান্য চ্যালেঞ্জিং করে তোলে। প্রথমটি গ্রন্থাগার। তারা কি সঠিকভাবে পাঠ্য পরিচালনা করে? উত্তরটি ... তারা চেষ্টা করে। আপনি যদি কোনও ওয়েব পৃষ্ঠা ডাউনলোড করেন তবে এলডাব্লুপি আপনার ফলাফলটিকে পাঠ্য হিসাবে ফিরিয়ে দেবে। যদি আপনি ফলাফলটিতে সঠিক পদ্ধতিটি কল করেন, তা হ'ল (এবং এটি হ'ল, এটি হ'ল decoded_content
না content
যা সার্ভার থেকে পাওয়া অক্টেট স্ট্রিম)) ডাটাবেস ড্রাইভাররা অস্থির হতে পারে; আপনি যদি কেবল পার্ল দিয়ে ডিবিডি :: এসকিউএলাইট ব্যবহার করেন তবে এটি কার্যকর হবে, তবে অন্য কোনও সরঞ্জাম যদি আপনার ডাটাবেসে ইউটিএফ -8 ব্যতীত অন্য কোনও এনকোডিং হিসাবে পাঠ্য সঞ্চিত করে রাখে ... ভাল ... এটি সঠিকভাবে পরিচালনা করা হবে না যতক্ষণ না আপনি এটিকে সঠিকভাবে পরিচালনা করতে কোড লিখেন।
আউটপুটটিং ডেটা সাধারণত সহজ হয় তবে আপনি যদি "প্রিন্টে বিস্তৃত অক্ষর" দেখেন তবে আপনি জানেন যে আপনি কোথাও এনকোডিংয়ের সাথে ঝামেলা করছেন। এই সতর্কতার অর্থ "আরে, আপনি পার্ল চরিত্রগুলি বহির্বিশ্বে ফাঁস করার চেষ্টা করছেন এবং এটি কোনও অর্থবোধ করে না"। আপনার প্রোগ্রামটি কাজ করে বলে মনে হচ্ছে (কারণ অন্য প্রান্তটি সাধারণত কাঁচা পার্ল অক্ষরগুলি সঠিকভাবে পরিচালনা করে) তবে এটি খুব ভাঙ্গা এবং কোনও মুহুর্তে কাজ বন্ধ করে দিতে পারে। একটি সুস্পষ্ট সঙ্গে এটি ঠিক করুন Encode::encode
!
দ্বিতীয় সমস্যাটি ইউটিএফ -8 এনকোডেড উত্স কোড। আপনি use utf8
প্রতিটি ফাইলের শীর্ষে না বললে পার্ল ধরে নেবে না যে আপনার উত্স কোডটি ইউটিএফ -8। এর অর্থ হ'ল প্রতিবার যখন আপনি কিছু বলবেন my $var = 'ほげ'
, আপনি আপনার প্রোগ্রামটিতে আবর্জনা ইনজেকশন দিচ্ছেন যা পুরোপুরি ভয়াবহভাবে ভেঙে দেবে। আপনাকে "utf8" ব্যবহার করতে হবে না, তবে আপনি যদি তা না করেন তবে আপনার প্রোগ্রামে আপনাকে অবশ্যই কোনও ASCII অক্ষর ব্যবহার করা উচিত নয়।
তৃতীয় সমস্যাটি পার্ল কীভাবে অতীতকে পরিচালনা করে। অনেক দিন আগে, ইউনিকোডের মতো কোনও জিনিস ছিল না এবং পার্ল ধরে নিয়েছিল যে সবকিছু ল্যাটিন -১ পাঠ্য বা বাইনারি ছিল। সুতরাং যখন ডেটা আপনার প্রোগ্রামে আসে এবং আপনি এটিকে পাঠ্য হিসাবে বিবেচনা করতে শুরু করেন, পার্ল প্রতিটি অক্টেটকে ল্যাটিন -1 চরিত্র হিসাবে বিবেচনা করে। এ কারণেই, যখন আমরা "文字 化 け" দৈর্ঘ্যের জন্য জিজ্ঞাসা করি, তখন আমরা 12 পেয়েছি। পার্ল ধরে নিয়েছে যে আমরা লাতিন -1 স্ট্রিং "æååã" (যা 12 টি অক্ষর, যার মধ্যে কিছুগুলি প্রিন্টিং রয়েছে) এ কাজ করছি।
এটিকে "অন্তর্নিহিত আপগ্রেড" বলা হয় এবং এটি করা একেবারে যুক্তিসঙ্গত জিনিস, তবে আপনার পাঠ্য ল্যাটিন -১ না হলে আপনি যা চান তা তা নয়। এজন্য সুস্পষ্টভাবে ইনপুট ডিকোড করা সমালোচনা: আপনি যদি এটি না করেন তবে পার্ল তা করবে এবং এটি এটি ভুল করতে পারে।
লোকেরা সমস্যায় পড়ে যেখানে তাদের অর্ধেক ডেটা সঠিক চরিত্রের স্ট্রিং এবং কিছু এখনও বাইনারি। পার্ল এখনও বাইনারি অংশটি ব্যাখ্যা করবে যদিও এটি ল্যাটিন -১ পাঠ্য এবং তারপরে এটি সঠিক চরিত্রের ডেটা সহ একত্রিত করবে। এটি আপনার চরিত্রগুলি সঠিকভাবে পরিচালনা করার মতো দেখায় যা আপনার প্রোগ্রামটি ভেঙে ফেলেছে, কিন্তু বাস্তবে আপনি এটি যথেষ্ট করেননি।
এখানে একটি উদাহরণ রয়েছে: আপনার একটি প্রোগ্রাম রয়েছে যা একটি ইউটিএফ-8-এনকোডযুক্ত পাঠ্য ফাইলটি পড়ে, আপনি PILE OF POO
প্রতিটি লাইনে একটি ইউনিকোড টেক করেন এবং আপনি এটি মুদ্রণ করেন। আপনি এটি লিখুন:
while(<>){
chomp;
say "$_ 💩";
}
এবং তারপরে কিছু ইউটিএফ -8 এনকোডড ডেটা চালান, যেমন:
perl poo.pl input-data.txt
এটি প্রতিটি লাইনের শেষে একটি পু দিয়ে ইউটিএফ -8 ডেটা মুদ্রণ করে। পারফেক্ট, আমার প্রোগ্রাম কাজ করে!
তবে না, আপনি কেবল বাইনারি সংক্ষেপণ করছেন। আপনি ফাইলটি থেকে অক্টেটগুলি পড়ছেন, চম্প \n
সহ একটি অপসারণ করছেন এবং তারপরে PILE OF POO
অক্ষরের UTF-8 উপস্থাপনায় বাইটগুলি সন্ধান করছেন । আপনি যখন ফাইল থেকে ডেটা ডিকোড করতে এবং আউটপুটটিকে এনকোড করার জন্য আপনার প্রোগ্রামটি সংশোধন করেন, আপনি লক্ষ্য করবেন যে আপনি পুর পরিবর্তে আবর্জনা ("ð ©") পেয়েছেন। এটি আপনাকে বিশ্বাস করতে পরিচালিত করবে যে ইনপুট ফাইলের ডিকোডিং করা ভুল কাজ। এটা না।
সমস্যাটি হ'ল পুটিকে সুস্পষ্টভাবে ল্যাটিন -১ হিসাবে আপগ্রেড করা হচ্ছে। আপনি যদি use utf8
বাইনারি পরিবর্তে আক্ষরিক পাঠ্য তৈরি করতে চান, তবে এটি আবার কাজ করবে!
(ইউনিকোডের সাহায্যে লোকদের সাহায্য করার সময় আমি এটাই প্রথম সমস্যাটি দেখতে পেয়েছি They তারা সঠিক অংশটি নিয়েছিল এবং এটি তাদের প্রোগ্রামটি ভেঙে দিয়েছে und এটি অপরিজ্ঞাত ফলাফলের জন্য দুঃখজনক: আপনি দীর্ঘদিন ধরে একটি কার্যকরী প্রোগ্রাম রাখতে পারেন, তবে আপনি যখন এটি মেরামত শুরু করেন, চিন্তাভাবনা করবেন না; আপনি যদি আপনার প্রোগ্রামে এনকোড / ডিকোড স্টেটমেন্ট যুক্ত করে থাকেন এবং এটি ভেঙে যায়, এর অর্থ কেবল আপনার আরও কাজ করা উচিত Next আরো সহজ!)
পার্ল এবং ইউনিকোড সম্পর্কে আপনার যা জানা দরকার তা সত্যিই এটি। যদি আপনি পার্লকে আপনার ডেটাটি বলে থাকেন তবে এর কাছে জনপ্রিয় সমস্ত প্রোগ্রামিং ভাষার মধ্যে ইউনিকোডের সেরা সমর্থন রয়েছে। আপনি যদি ধরে নেন যে এটি যাদুকরীভাবে জানা যাবে যে আপনি এটি কোন ধরণের পাঠ্য খাওয়াচ্ছেন, তবে, আপনি নিজের ডেটা অলঙ্ঘনীয়ভাবে ট্র্যাশ করতে চলেছেন। কেবলমাত্র আপনার প্রোগ্রামটি আজ আপনার ইউটিএফ -8 টার্মিনালে কাজ করে এর অর্থ এই নয় যে এটি আগামীকাল কোনও ইউটিএফ -16 এনকোডযুক্ত ফাইলটিতে কাজ করবে। সুতরাং এখনই এটি নিরাপদ করুন এবং আপনার ব্যবহারকারীর ডেটা ট্র্যাশ করার মাথাব্যথা নিজেকে বাঁচান!
ইউনিকোড পরিচালনা করার সহজ অংশটি এনকোডিং আউটপুট এবং ডিকোডিং ইনপুট। শক্ত অংশটি আপনার সমস্ত ইনপুট এবং আউটপুট সন্ধান করছে এবং এটি কোন এনকোডিং তা নির্ধারণ করছে। তবে সে কারণেই আপনি বড় টাকা পেয়েছেন :)