আমি পাইথোনিস্টাসের ক্রোধকে ডাকতে পারি (আমি পাইথনটি বেশি ব্যবহার করি না বলে জানি না) বা অন্যান্য ভাষাগুলির প্রোগ্রামাররা এই উত্তরটি সহ উত্তর দিতে পারেন তবে আমার মতে বেশিরভাগ ফাংশনগুলিতে আদর্শভাবে বলতে গেলে কোনও ব্লক থাকা উচিত নয়catch
। কেন তা দেখানোর জন্য, আমাকে এটি 80 এর দশকের শেষের দিকে এবং 90 এর দশকের গোড়ার দিকে টার্বো সি এর সাথে কাজ করার সময় ম্যানুয়াল ত্রুটি কোড প্রচারের সাথে আমার বিপরীতে তুলনা করুন।
সুতরাং আসুন আমরা বলি যে কোনও ব্যবহারকারী লোড করার জন্য একটি চিত্র ফাইল নির্বাচন করার প্রতিক্রিয়ায় একটি চিত্র বা এর মতো কিছু লোড করার জন্য আমাদের একটি ফাংশন রয়েছে এবং এটি সি এবং অ্যাসেমব্লিতে লেখা আছে:
আমি কয়েকটি নিম্ন-স্তরের ফাংশন বাদ দিয়েছি তবে আমরা দেখতে পাচ্ছি যে আমি ত্রুটি-পরিচালনা সংক্রান্ত তাদের যে কী দায়িত্ব রয়েছে তার উপর ভিত্তি করে রঙের কোডেড বিভিন্ন বিভাগের ফাংশনগুলি চিহ্নিত করেছি।
ব্যর্থতা এবং পুনরুদ্ধারের পয়েন্ট
এখন ফাংশনগুলির বিভাগগুলি লিখতে কখনই কঠিন ছিল না আমি "ব্যর্থতার সম্ভাব্য বিন্দু" (যেগুলি throw
, অর্থাৎ) এবং "ত্রুটি পুনরুদ্ধার এবং প্রতিবেদন" ফাংশনগুলি (এটি catch
, যা ) বলি ।
ঐ ফাংশন সবসময় লিখতে সঠিকভাবে সামনে ব্যতিক্রম হ্যান্ডলিং উপলব্ধ ছিল একটি ফাংশন যে মেমরি বরাদ্দ করতে ব্যর্থ মত একটি বহিস্থিত ব্যর্থতা মধ্যে চালাতে পারেন,, শুধু একটি আসতে পারেন যেহেতু তুচ্ছ ছিল NULL
বা 0
বা -1
বা একটি বিশ্বব্যাপী ত্রুটি কোড বা এই প্রভাব কিছু সেট। এবং ত্রুটি পুনরুদ্ধার / রিপোর্টিং সর্বদা সহজ ছিল যেহেতু একবার আপনি কল স্ট্যাকের পথে এমন এক পর্যায়ে কাজ করেছিলেন যেখানে ব্যর্থতাগুলি পুনরুদ্ধার করা এবং রিপোর্ট করা বুদ্ধিমান হয়ে যায়, আপনি কেবল ত্রুটি কোড এবং / অথবা বার্তাটি গ্রহণ করেন এবং এটি ব্যবহারকারীকে রিপোর্ট করেন। এবং স্বাভাবিকভাবেই এই শ্রেণিবিন্যাসের পাতায় একটি ফাংশন যা ভবিষ্যতে এটি কীভাবে পরিবর্তিত হয় তা কখনই ব্যর্থ হতে পারে না Convert Pixel
) সঠিকভাবে লিখতে (কমপক্ষে ত্রুটি পরিচালনার ক্ষেত্রে সম্মতি দিয়ে) মরে যাওয়া সহজ is
ত্রুটি প্রচার
তবে, মানব ত্রুটির প্রবণ ক্লান্তিকর কাজগুলি হ'ল ত্রুটি প্রচারকারী , যেগুলি সরাসরি ব্যর্থতার মধ্যে পড়ে না তবে এমন ক্রিয়াকলাপ বলে যেগুলি শ্রেণিবদ্ধের আরও গভীরতর জায়গায় ব্যর্থ হতে পারে। এই মুহুর্তে, Allocate Scanline
হতে পারে একটি ব্যর্থতা হ্যান্ডেল করতে malloc
এবং তারপরে একটি ত্রুটি নীচে ফিরে আসতে হবে Convert Scanlines
, তারপরে Convert Scanlines
সেই ত্রুটিটি পরীক্ষা করে এটি Decompress Image
, তারপরে Decompress Image->Parse Image
এবং Parse Image->Load Image
, এবং Load Image
ব্যবহারকারী-এন্ড কমান্ডের কাছে দিতে হবে যেখানে শেষ পর্যন্ত ত্রুটিটি রিপোর্ট করা হয়েছে ।
এখান থেকেই প্রচুর মানুষ ভুল করে যেহেতু ত্রুটিটি সঠিকভাবে পরিচালনা করার ক্ষেত্রে ক্রিয়াকলাপের পুরো ক্রমক্রমটি নীচে নেমে আসতে ত্রুটিটি পরীক্ষা করতে ব্যর্থ করতে কেবল একটি ত্রুটি প্রচারকারী লাগে।
তদ্ব্যতীত, যদি ত্রুটি কোডগুলি ফাংশন দ্বারা ফিরিয়ে দেওয়া হয়, তবে আমরা বলি যে আমাদের কোডবেসের 90%, সাফল্যের উপর আগ্রহের মানগুলি ফিরিয়ে দেওয়ার ক্ষমতাটি হারাতে পারায় যেহেতু অনেকগুলি ক্রিয়াকলাপে ত্রুটি কোড ফেরত দেওয়ার জন্য তাদের রিটার্ন মান সংরক্ষণ করতে হবে ব্যর্থতা ।
হ্রাস মানব ত্রুটি: গ্লোবাল ত্রুটি কোডগুলি
তাহলে আমরা কীভাবে মানুষের ত্রুটির সম্ভাবনা হ্রাস করতে পারি? এখানে আমি কিছু সি প্রোগ্রামারদের ক্রোধেরও আহ্বান জানাতে পারি, তবে আমার মতে একটি তাত্ক্ষণিক উন্নতি হ'ল ওপেনজিএল এর মতো গ্লোবাল ত্রুটি কোডগুলি ব্যবহার করা glGetError
। এটি কমপক্ষে সাফল্যের উপর সুদের অর্থবোধক মূল্যগুলি ফিরিয়ে দিতে ফাংশনকে মুক্ত করে। এই থ্রেডটিকে নিরাপদ এবং কার্যকর করার উপায় রয়েছে যেখানে ত্রুটি কোডটি থ্রেডে স্থানীয়করণ করা হয়।
এমনও কিছু ঘটনা রয়েছে যেখানে কোনও ফাংশন কোনও ত্রুটির মধ্যে দিয়ে যেতে পারে তবে পূর্ববর্তী ত্রুটিটি আবিষ্কারের ফলে অকালপূর্বে ফিরে আসার আগে এটি কিছুটা বেশি সময় চালিয়ে যাওয়া অপেক্ষাকৃত নিরীহ। এটি প্রতিটি একক ক্রিয়াকলাপে 90% ফাংশন কলগুলির বিরুদ্ধে ত্রুটিগুলি পরীক্ষা না করেই এ জাতীয় কিছু ঘটতে দেয়, সুতরাং এটি এতটুকু সাবধানতা ছাড়াই সঠিক ত্রুটি পরিচালনার অনুমতি দিতে পারে।
মানব ত্রুটি হ্রাস করা: ব্যতিক্রম-পরিচালনা
তবে, ম্যানুয়াল ত্রুটি প্রচারের নিয়ন্ত্রণ প্রবাহের দিকটি মোকাবেলার জন্য উপরের সমাধানটির এখনও অনেকগুলি ফাংশন প্রয়োজন, এমনকি যদি এটি ম্যানুয়াল if error happened, return error
ধরণের কোডের লাইনের সংখ্যা হ্রাস করে । এটি এটিকে পুরোপুরি সরিয়ে ফেলবে না কারণ এখনও প্রায়শই একটি ত্রুটির জন্য কমপক্ষে একটি জায়গা যাচাই করা এবং প্রায় প্রতিটি ত্রুটি প্রচারের জন্য ফিরে আসা প্রয়োজন। দিনটি বাছাই করতে ব্যতিক্রম-হ্যান্ডলিং ছবিটিতে আসে তাই এটি হয়।
তবে এখানে ব্যতিক্রম হ্যান্ডলিংয়ের মান হ'ল ম্যানুয়াল ত্রুটি প্রচারের নিয়ন্ত্রণ প্রবাহের দিকটি মোকাবেলার প্রয়োজন মুক্ত করা। এর অর্থ এর কোডটি catch
আপনার কোডবেজ জুড়ে কোনও নৌকা বোঝা চাপতে এড়াতে সক্ষমতার সাথে আবদ্ধ । উপরের চিত্রটিতে, কেবলমাত্র যেখানে catch
ব্লক থাকা উচিত Load Image User Command
সেখানেই ত্রুটিটি প্রতিবেদন করা হয়েছে। অন্য কিছুতে আদর্শভাবে কিছু হওয়া উচিত নয় catch
কারণ অন্যথায় এটি তাত্ক্ষণিক এবং ত্রুটিযুক্ত কোড হ্যান্ডলিংয়ের মতো ত্রুটি-প্রবণ হিসাবে পেতে শুরু করেছে।
সুতরাং যদি আপনি আমাকে জিজ্ঞাসা করেন, যদি আপনার কাছে এমন কোনও কোডবেস রয়েছে যা মার্জিত উপায়ে ব্যতিক্রম হ্যান্ডলিং থেকে সত্যিই উপকৃত হয় তবে এর সর্বনিম্ন সংখ্যার catch
ব্লক থাকা উচিত (নূন্যতম দ্বারা আমি শূন্য নয়, তবে প্রতিটি অনন্য হাই- শেষ ব্যবহারকারীর ক্রিয়াকলাপ যা ব্যর্থ হতে পারে এবং সমস্ত উচ্চ-ব্যবহারকারীর ক্রিয়াকলাপ কেন্দ্রীয় কমান্ড সিস্টেমের মাধ্যমে আহ্বান করা হলেও সম্ভবত কম))
রিসোর্স ক্লিনআপ
যাইহোক, ব্যতিক্রম-পরিচালনা কেবলমাত্র মৃত্যুদন্ড কার্যকর হওয়ার সাধারণ প্রবাহ থেকে পৃথক ব্যতিক্রমী পাথগুলিতে ত্রুটি প্রচারের নিয়ন্ত্রণ প্রবাহের দিকগুলি ম্যানুয়ালি এড়ানোর প্রয়োজন সমাধান করে। প্রায়শই একটি ফাংশন যা ত্রুটি প্রচারকারী হিসাবে কাজ করে, এটি যদি এখন স্বয়ংক্রিয়ভাবে এটিএইচ এর সাথে করে, তবুও এটি ধ্বংস করার জন্য প্রয়োজনীয় কিছু সংস্থান অর্জন করতে পারে। উদাহরণস্বরূপ, এই জাতীয় ফাংশন কোনও অস্থায়ী ফাইলটি খুলতে পারে যা ফাংশন থেকে ফিরে আসার আগে তা বন্ধ হওয়া দরকার, বা যে কোনও বিষয়ই আনলক করার জন্য কোনও মিউটেক্স লক করা দরকার।
এর জন্য, আমি বিভিন্ন প্রকারের ভাষা থেকে প্রচুর প্রোগ্রামারদের ক্রোধের উদ্রেক করতে পারি, তবে আমি মনে করি এটিতে সি ++ পদ্ধতির পক্ষে আদর্শ। ভাষা এমন ধ্বংসকারীদের সাথে পরিচয় করিয়ে দেয় যা তাত্ক্ষণিকভাবে কোনও বস্তুর সুযোগের বাইরে চলে যায় এমন একটি তাত্ক্ষণিক ফ্যাশনে ডাকা হয়। এর কারণে, সি ++ কোড যা বলে, একটি স্কেপড মুউটেক্স অবজেক্টটির মাধ্যমে একটি মুটেক্সকে একটি ডেস্ট্রাক্টরের সাথে লক করে রাখে ম্যানুয়ালি এটিকে আনলক করা দরকার না, কারণ যখনই বস্তুটি স্কোপের বাইরে চলে যায় তবে তা স্বয়ংক্রিয়ভাবে আনলক হয়ে যায় (যাই হোক না কেন ব্যতিক্রম হলেও সম্মুখীন)। সুতরাং স্থানীয় রিসোর্স ক্লিনআপের সাথে মোকাবিলা করার জন্য কোনও ভাল লিখিত সি ++ কোডের দরকার নেই।
যে ভাষাগুলিতে ডেস্ট্রাক্টর নেই, তাদের finally
স্থানীয় ব্লকগুলি ম্যানুয়ালি পরিষ্কার করার জন্য একটি ব্লক ব্যবহার করা প্রয়োজন । এটি বলে, এটি আপনার কোডটি ম্যানুয়াল ত্রুটি প্রচারের সাথে জড়িত হতে পারে তবে শর্ত থাকে যে আপনি যদি catch
সমস্ত ফ্রিকিং জায়গাতে ব্যতিক্রম না হন।
বাহ্যিক পার্শ্ব প্রতিক্রিয়া বিপরীত
এই সমাধানের জন্য সবচেয়ে কঠিন ধারণাগত সমস্যা। যদি কোনও ক্রিয়াকলাপ, এটি কোনও ত্রুটি প্রচারক বা ব্যর্থতার বিন্দু বাহ্যিক পার্শ্ব প্রতিক্রিয়া সৃষ্টি করে, তবে সিস্টেমটিকে একটি অবস্থায় ফিরিয়ে আনার জন্য সেই পার্শ্ব প্রতিক্রিয়াগুলি "পূর্বাবস্থায়িত" করা দরকার যদিও অপারেশনটি কখনও ঘটেনি, " অর্ধ-বৈধ "রাষ্ট্র যেখানে অর্ধেক অভিযান সফল হয়েছিল। আমি এমন কোন ভাষা সম্পর্কে জানি না যা এই ধারণাগত সমস্যাটিকে আরও সহজ করে তোলে এমন ভাষা ব্যতীত যেগুলি প্রথমে বাহ্যিক পার্শ্ব প্রতিক্রিয়া সৃষ্টি করার জন্য বেশিরভাগ ফাংশনের প্রয়োজনকে কমিয়ে দেয়, যেমন কার্যকরী ভাষাগুলি যা অপরিবর্তনীয়তা এবং অবিরাম ডাটা স্ট্রাকচারের চারদিকে ঘোরে।
এখানে finally
, সেখানে পরিবর্তনশীলতা এবং পার্শ্ব প্রতিক্রিয়া চারপাশে ঘুরপাক ভাষায় সমস্যার সবচেয়ে মার্জিত সমাধান মধ্যে তর্কসাপেক্ষে কারণ প্রায়ই যুক্তিবিজ্ঞান এই ধরনের একটি নির্দিষ্ট ফাংশন খুব নির্দিষ্ট এবং "রিসোর্স পরিষ্করণ ধারণা থেকে এত ভাল মানচিত্র নেই "। finally
আপনার এই catch
ব্লকটি দরকার কিনা তা বিবেচনা না করেই আপনার ফাংশনটি সমর্থন করে এমন ভাষাগুলিতে পার্শ্ব প্রতিক্রিয়াগুলির বিপরীত হয়েছে কিনা তা নিশ্চিত করার জন্য আমি এই ক্ষেত্রে উদারভাবে ব্যবহার করার পরামর্শ দিচ্ছি (এবং আবার, আপনি যদি আমাকে জিজ্ঞাসা করেন, ভাল লিখিত কোডের ন্যূনতম সংখ্যার সংখ্যা থাকতে হবে) catch
ব্লকগুলি এবং সমস্ত catch
ব্লক এমন জায়গাগুলিতে হওয়া উচিত যেখানে এটি উপরের চিত্রের সাথে সর্বাধিক অর্থবোধ করে Load Image User Command
)।
স্বপ্নের ভাষা
যাইহোক, আইএমও finally
পার্শ্ব প্রতিক্রিয়া বিপরীতের জন্য আদর্শের কাছাকাছি তবে বেশ নয়। boolean
অকাল প্রস্থান (নিক্ষিপ্ত ব্যতিক্রম বা অন্যথায়) এর ক্ষেত্রে পার্শ্ব প্রতিক্রিয়াগুলি কার্যকরভাবে পিছনে রোল করতে আমাদের একটি পরিবর্তনশীল প্রবর্তন করতে হবে :
bool finished = false;
try
{
// Cause external side effects.
...
// Indicate that all the external side effects were
// made successfully.
finished = true;
}
finally
{
// If the function prematurely exited before finishing
// causing all of its side effects, whether as a result of
// an early 'return' statement or an exception, undo the
// side effects.
if (!finished)
{
// Undo side effects.
...
}
}
আমি যদি কোনও ভাষা ডিজাইন করতে পারি তবে এই সমস্যাটি সমাধানের আমার স্বপ্নের উপায়টি উপরের কোডটি স্বয়ংক্রিয় করার মতো হবে:
transaction
{
// Cause external side effects.
...
}
rollback
{
// This block is only executed if the above 'transaction'
// block didn't reach its end, either as a result of a premature
// 'return' or an exception.
// Undo side effects.
...
}
... স্থানীয় সম্পদের পরিচ্ছন্নতা স্বয়ংক্রিয় করার জন্য ধ্বংসকারীদের সাথে এটি তৈরি করা যাতে আমাদের কেবল প্রয়োজন হয় transaction
, rollback
এবং catch
(যদিও আমি এখনও finally
সি সংস্থানগুলির সাথে নিজেকে যুক্ত করতে চাই না বলে যুক্ত করতে চাই)। যাইহোক, finally
একটি boolean
ভেরিয়েবলের সাথে এটিকে সোজা করে তোলার সবচেয়ে কাছের জিনিসটি আমি এখনও পর্যন্ত আমার স্বপ্নের ভাষার অভাব পেয়েছি। এর জন্য দ্বিতীয় দ্বিতীয়টি সহজ সমাধান আমি পেয়েছি সি ++ এবং ডি এর মতো ভাষাগুলির স্কোপ গার্ড , তবে আমি সর্বদা স্কোপ গার্ডদেরকে ধারণা থেকে খানিকটা বিশ্রী দেখতে পাই যেহেতু এটি "রিসোর্স ক্লিনআপ" এবং "পার্শ্ব প্রতিক্রিয়া বিপরীত" ধারণাটিকে ঝাপসা করে। আমার মতে এগুলি খুব আলাদা ধারণা যা আলাদাভাবে মোকাবেলা করতে হবে।
কোনও ভাষার আমার ছোট পাইপ স্বপ্নটি অপরিবর্তনযোগ্যতা এবং অবিচ্ছিন্ন ডাটা স্ট্রাকচারের চারপাশে প্রচুর পরিমাণে ঘুরে বেড়াত যাতে প্রয়োজনীয় না হলেও দক্ষ কার্যকরী রচনার জন্য যা কার্যকরী কারণে সত্ত্বেও বৃহত্তর ডেটা স্ট্রাকচারকে গভীরভাবে অনুলিপি করতে হয় না। কোন পার্শ্ব প্রতিক্রিয়া।
উপসংহার
যাইহোক যাইহোক, আমার রামফুলগুলি একপাশে রেখে, আমি মনে করি try/finally
যে সকেটটি বন্ধ করার জন্য আপনার কোডটি দুর্দান্ত এবং দুর্দান্ত তা বিবেচনা করে যে পাইথনের সিস্ট্রিক্ট ডিস্ট্রাস্টারগুলির সমতুল্য নেই, এবং আমি ব্যক্তিগতভাবে মনে করি যে সেই জায়গাগুলির জন্য আপনার সেই উদারভাবে ব্যবহার করা উচিত যা পার্শ্ব প্রতিক্রিয়াগুলি বিপরীতমুখী করতে হবে need এবং আপনাকে catch
যে জায়গাগুলি সর্বাধিক বোধগম্য করতে হবে সেখানে যে সংখ্যাগুলি হ্রাস করতে হবে।