সাফল্য বা ব্যর্থতা যখন বুলিয়ান ফিরে আসা একমাত্র উদ্বেগ


15

আমি প্রায়শই নিজেকে কোনও পদ্ধতি থেকে বুলেটিয়ান ফেরত পেতে দেখি যা একাধিক স্থানে ব্যবহৃত হয়, সেই পদ্ধতিটির চারপাশে সমস্ত যুক্তি এক জায়গায় রাখার জন্য। সমস্ত (অভ্যন্তরীণ) কলিং পদ্ধতিটি জানা দরকার যে অপারেশন সফল হয়েছিল কি না।

আমি পাইথন ব্যবহার করছি তবে প্রশ্নটি অবশ্যই সেই ভাষার সাথে নির্দিষ্ট নয়। আমি কেবল দুটি বিকল্পই ভাবতে পারি

  1. পরিস্থিতি ব্যতিক্রমী না হলেও একটি ব্যতিক্রম উত্থাপন করুন, এবং ফাংশনটি বলা হয় এমন জায়গাতেই সেই ব্যতিক্রমটি ধরা মনে রাখবেন
  2. আমি করছি বলে একটি বুলিয়ান ফেরত দিন।

এটি সত্যিই একটি সহজ উদাহরণ যা প্রমাণ করে যে আমি কী বলছি।

import os

class DoSomething(object):

    def remove_file(self, filename):

        try:
            os.remove(filename)
        except OSError:
            return False

        return True

    def process_file(self, filename):

        do_something()

        if remove_file(filename):
            do_something_else()

যদিও এটি কার্যকরী, তবে কিছু করার এই পদ্ধতিটি আমি সত্যিই অপছন্দ করি, এটি "গন্ধযুক্ত" হয় এবং এর ফলে মাঝে মাঝে প্রচুর নেস্টেড আইএফ হতে পারে। তবে, আমি সহজ উপায় সম্পর্কে ভাবতে পারি না।

আমি আরও এলবিওয়াইএল দর্শনের দিকে ফিরে যেতে পারি এবং os.path.exists(filename)মুছে ফেলার চেষ্টা করার আগে ব্যবহার করতে পারি তবে এর মধ্যে কোনও ফাইল লক না হওয়ার কোনও গ্যারান্টি নেই (এটি অসম্ভব তবে সম্ভব) এবং মুছে ফেলা সফল হয়েছে কিনা তা এখনও নির্ধারণ করতে হবে।

এটি কি একটি "গ্রহণযোগ্য" ডিজাইন এবং যদি না হয় তবে এটির নকশা করার আরও ভাল উপায় কী হতে পারে?

উত্তর:


11

booleanযখন পদ্ধতি / ফাংশনটি যৌক্তিক সিদ্ধান্ত নিতে কার্যকর হয় তখন আপনার ফিরে আসা উচিত ।

আপনি একটি নিক্ষেপ করা উচিত exceptionপদ্ধতি / ফাংশন সম্ভবত যৌক্তিক সিদ্ধান্ত ব্যবহার করা হয় না যখন।

ব্যর্থতাটি কতটা গুরুত্বপূর্ণ, এবং যদি এটি পরিচালনা করা উচিত বা না হয় সে সম্পর্কে আপনাকে সিদ্ধান্ত নিতে হবে। যদি আপনি ব্যর্থতাটিকে সতর্কতা হিসাবে শ্রেণীবদ্ধ করতে পারেন তবে ফিরে আসুন boolean। যদি অবজেক্টটি কোনও খারাপ অবস্থায় প্রবেশ করে যা ভবিষ্যতে কলগুলিকে অস্থির করে তোলে তবে একটি নিক্ষেপ করুন exception

আর একটি অনুশীলন হচ্ছে objectsফলাফলের পরিবর্তে ফিরে আসা । আপনি যদি কল করেন open, তবে এটি কোনও Fileবস্তু ফেরত দেওয়া উচিত বা nullখুলতে অক্ষম হলে। এটি নিশ্চিত করে যে প্রোগ্রামারদের একটি অবজেক্ট উদাহরণ রয়েছে যা বৈধ অবস্থায় রয়েছে যা ব্যবহার করা যেতে পারে।

সম্পাদনা করুন:

মনে রাখবেন যে বেশিরভাগ ভাষা কোনও ফাংশনের ফলাফল বুলিয়ান বা পূর্ণসংখ্যার ক্ষেত্রে এড়িয়ে যায়। সুতরাং যখন ফলাফলের জন্য কোনও বাম হাতের অ্যাসাইনমেন্ট নেই তখন ফাংশনটি কল করা সম্ভব। বুলিয়ান ফলাফলের সাথে কাজ করার সময়, সবসময় ধরে নিন প্রোগ্রামার প্রত্যাবর্তিত মানটিকে অগ্রাহ্য করছে এবং এটি ব্যতিক্রম হওয়া উচিত কিনা তা সিদ্ধান্ত নিতে এটি ব্যবহার করুন।


এটি আমি যা করছি তার একটি বৈধতা যা আমি উত্তরটি পছন্দ করি :-)। বস্তুগুলির বিষয়ে, যদিও আমি বুঝতে পেরেছি আপনি কোথা থেকে আসছেন আমি তা দেখতে পাচ্ছি না এটি বেশিরভাগ ক্ষেত্রে এটি কীভাবে ব্যবহার করবে। আমি DRY হতে চাই তাই আমি একক পদ্ধতিতে অবজেক্টটিকে পুনরায় সংযুক্ত করতে যাচ্ছি কারণ আমি কেবল এটির জন্য একটি কাজ করতে চাই। আমি এখন আমার কাছে একই কোডটি রেখেছি, একটি অতিরিক্ত পদ্ধতি দিয়ে সংরক্ষণ করুন। (প্রদত্ত উদাহরণের জন্যও আমি ফাইলটি মুছছি তাই কোনও নাল ফাইল অবজেক্টটি বেশি কিছু বলে না :-)
বেন

মুছে ফেলা জটিল, কারণ এটির নিশ্চয়তা নেই। আমি কোনও ফাইল মুছে ফেলার পদ্ধতিটি কখনও একটি ব্যতিক্রম ছুঁড়ে দেখিনি, তবে প্রোগ্রামার ব্যর্থ হলে কী করতে পারে? ক্রমাগত লুপ আবার চেষ্টা করছেন? না এটি একটি ওএস সমস্যা। কোডটি ফলাফলটি লগ করে এগিয়ে চলতে হবে।
১act:৪৯-এ সংশোধনীয়

4

এটি সম্পর্কে আপনার স্বজ্ঞাততা সঠিক, এটি করার আরও ভাল উপায় আছে: মনডস

মোনাড কি?

শ্যাডিংয়ের প্রক্রিয়াটি গোপন করার সময় মনডগুলি একসাথে চেইন ক্রিয়াকলাপের এক উপায় (উইকিপিডিয়াকে প্যারাফ্রেস করতে) হয়; আপনার ক্ষেত্রে শৃঙ্খলাকৃতি হল নেস্টেড ifএস। এটি লুকান এবং আপনার কোডটি খুব সুন্দর গন্ধ পাবে ।

সেখানে বেশ কয়েকটি মোনাড রয়েছে যা কেবল "(সম্ভবত" এবং "হয়") করবে এবং আপনার জন্য ভাগ্যবান তারা সত্যই একটি অজগর মনড লাইব্রেরির অংশ!

তারা আপনার কোডের জন্য কী করতে পারে

এখানে "হয়" মোনাদ (লিঙ্কযুক্ত গ্রন্থাগারে "" উপলব্ধ ") ব্যবহার করে এখানে একটি উদাহরণ দেওয়া হয়েছে, যেখানে কোনও ফাংশন যা ঘটেছে তার উপর নির্ভর করে সাফল্য বা ব্যর্থতা ফিরিয়ে দিতে পারে:

import os

class DoSomething(object):

    def remove_file(self, filename):
        try:
            os.remove(filename)
            return Success(None)
        except OSError:
            return Failure("There was an OS Error.")

    @do(Failable)
    def process_file(self, filename):
        do_something()
        yield remove_file(filename)
        do_something_else()
        mreturn(Success("All ok."))

এখন, এটি আপনার এখনকার তুলনায় খুব বেশি আলাদা না দেখায়, তবে আপনার যদি আরও বেশি অপারেশন হয় যার ফলে ব্যর্থতার কারণ হতে পারে তবে কীভাবে হবে তা বিবেচনা করুন:

    def action_that_might_fail_and_returns_something(self):
        # get some random value between 0 and 1 here
        if value < 0.5:
            return Success(value)
        else:
            return Failure("Bad value! Bad! Go to your room!")

    @do(Failable)
    def process_file(self, filename):
        do_something()
        yield remove_file(filename)
        yield action_that_might_fail(somearg)
        yield another_action_that_might_fail(someotherarg)
        some_val = yield action_that_might_fail_and_returns_something()
        yield something_that_used_the_return_value(some_val)
        do_something_else()
        mreturn(Success("All ok."))

প্রতিটি yieldমধ্যে গুলি process_fileফাংশন, যদি ফাংশন কল ব্যর্থ ফেরৎ তারপর process_fileফাংশন আউট থেকে প্রস্থান করবে, যে সময়ে , ব্যর্থ ফাংশন থেকে ব্যর্থতা মান ফিরে, পরিবর্তে বাকি উপর চালিয়ে যাওয়া এবং ফিরেSuccess("All ok.")

এখন, নেস্টেড ifগুলি দিয়ে উপরেরটি করার কল্পনা করুন ! (আপনি কীভাবে রিটার্ন মানটি পরিচালনা করবেন !?)

উপসংহার

মনডস দুর্দান্ত :)


মন্তব্য:

আমি পাইথন প্রোগ্রামার নই - কিছু প্রকল্প অটোমেশনের জন্য আমি নিনদা'র স্ক্রিপ্টে উপরের সাথে লিঙ্কিত মনাদ গ্রন্থাগারটি ব্যবহার করেছি। যদিও আমি একত্রিত হয়েছি যে সাধারণভাবে ব্যতিক্রমগুলি ব্যবহার করার জন্য পছন্দসই, আইডিয়োম্যাটিক পদ্ধতি is

আইআইআরসি পাতায় লিবিব স্ক্রিপ্টে একটি টাইপো রয়েছে যদিও আমি এটিটি এটি ভুলে গিয়েছি। আমার মনে পড়লে আপডেট করব। আমি পৃষ্ঠার বিরুদ্ধে আমার সংস্করণ diff'd এবং পাওয়া যায়নি: def failable_monad_examle():-> def failable_monad_example():- pএর মধ্যে exampleঅনুপস্থিত ছিল।

কোনও ফ্যাবিলিটি সজ্জিত ফাংশনের ফলাফল পেতে (যেমন process_file) আপনাকে ফলাফলটি একটিতে ক্যাপচার করতে হবে এবং এটি পেতে variableএকটি variable.valueকরতে হবে।


2

একটি ফাংশন একটি চুক্তি, এবং এর নামটি প্রস্তাব দেয় যে এটি কোন চুক্তিটি পূর্ণ করবে। আইএমএইচও, আপনি যদি নামটি দিয়ে থাকেন তবে এটি remove_fileফাইলটি সরিয়ে ফেলা উচিত এবং এটি করতে ব্যর্থ হওয়া ব্যতিক্রমের কারণ হতে পারে। অন্যদিকে, আপনি যদি এটির নাম দেন try_remove_file, ফাইলটি অপসারণ করা হয়েছে কিনা তা মুছে ফেলার জন্য এবং "বুলিয়ান" ফিরিয়ে দেওয়ার জন্য "চেষ্টা" করা উচিত।

এটি অন্য একটি প্রশ্নে নিয়ে যায় - এটি হওয়া উচিত remove_fileনাকি try_remove_file? এটি আপনার কল সাইটে নির্ভর করে। আসলে, আপনার উভয় পদ্ধতি থাকতে পারে এবং সেগুলিকে বিভিন্ন দৃশ্যে ব্যবহার করতে পারেন তবে আমি মনে করি যে প্রতি-সেফ ফাইল অপসারণের সাফল্যের উচ্চ সম্ভাবনা রয়েছে তাই remove_fileব্যর্থ হলে আমি কেবল সেই ছোঁড়া ব্যতিক্রমই পছন্দ করি।


0

এই বিশেষ ক্ষেত্রে আপনি কেন ফাইলটি সরাতে পারবেন না তা ভেবে ভাবতে দরকারী। আসুন বলি যে সমস্যাটি হ'ল ফাইলটি থাকতে পারে বা থাকতে পারে। তারপরে আপনার একটি ফাংশন থাকা উচিত doesFileExist()যা সত্য বা মিথ্যা প্রত্যাবর্তন করে এবং এমন একটি ফাংশন removeFile()যা কেবল ফাইলটি মুছে দেয়।

আপনার কোডে আপনি প্রথমে ফাইলটি উপস্থিত আছে কিনা তা পরীক্ষা করে দেখতে হবে। যদি তা হয়, কল করুন removeFile। যদি তা না হয় তবে অন্য জিনিসগুলি করুন।

এই ক্ষেত্রে যদি আপনি removeFileফাইলটি অন্য কোনও কারণে যেমন অনুমতি ছাড়াই অপসারণ করা না যায় তবে আপনি একটি ব্যতিক্রম ছুঁড়ে ফেলতে চাইতে পারেন।

সংক্ষেপে বলতে গেলে, ব্যতিক্রমী জিনিসগুলির জন্য ব্যতিক্রম ছুঁড়ে ফেলা উচিত well সুতরাং যদি এটি পুরোপুরি স্বাভাবিক হয় যে আপনি যে ফাইলটি মুছার চেষ্টা করছেন সেটি উপস্থিত নাও থাকতে পারে, তবে এটি ব্যতিক্রম নয়। এটি পরীক্ষা করার জন্য একটি বুলিয়ান প্রিকেট লিখুন। অন্যদিকে, যদি আপনার কাছে ফাইলটির লেখার অনুমতি না থাকে বা হঠাৎ অ্যাক্সেসযোগ্য এমন কোনও দূরবর্তী ফাইল সিস্টেমে থাকে তবে সেগুলি খুব ভাল ব্যতিক্রমী শর্ত হতে পারে।


আমি যে উদাহরণ দিয়েছি তার সাথে এটি অত্যন্ত সুনির্দিষ্ট which আমি এটি এখনও লিখিনি, এটি ফাইল সংরক্ষণাগারভুক্ত এবং লগইন করে যা ডাটাবেসে ঘটেছে। ফাইলগুলি যে কোনও সময় পুনরায় লোড করা যায় (যদিও একবারে লোড হওয়া ফাইলগুলি পুনরায় লোড হওয়ার সম্ভাবনা খুব কম থাকে) এটি সম্ভব যে কোনও ফাইল চেক এবং মোছার প্রচেষ্টাটির মধ্যে অন্য প্রক্রিয়া দ্বারা লক করা যায়। ব্যর্থতা ব্যতিক্রমী কিছুই নেই। প্রথমে চেক করতে বিরত না হওয়া এবং উত্থাপিত ব্যতিক্রমটি (যদি প্রয়োজন হয়) ধরতে না পারা এটি স্ট্যান্ডার্ড পাইথন, আমি এবার এটির সাথে কিছুই করতে চাই না।
বেন

ব্যর্থতা সম্পর্কে যদি ব্যতিক্রমী কিছু না থাকে, তবে আপনি কোনও ফাইল অপসারণ করতে পারবেন কিনা তা পরীক্ষা করা আপনার প্রোগ্রামের যুক্তির একটি বৈধ অঙ্গ। একক দায়িত্বের নীতি নির্দেশ দেয় যে আপনার একটি চেক ফাংশন এবং একটি সরানো ফাইল ফাংশন থাকা উচিত।
Dima
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.