জাভাতে নালাগুলি চেক না করেই একটি মান সংগ্রহ করা


15

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

আমি একটি খুব সাধারণ রুটিন লিখেছি যা কোনও অবজেক্ট আনার সময় আমাকে নাল চেকিং এড়াতে দেয় ...

public final class NoNPE {

    public static <T> T get(NoNPEInterface<T> in) {
        try {
            return in.get();
        } catch (NullPointerException e) {
            return null;
        }
    }

    public interface NoNPEInterface<T> {
        T get();
    }
}

আমি এটি কিছুটা এভাবে ব্যবহার করি ...

Room room = NoNPE.get(() -> country.getTown().getHouses().get(0).getLivingRoom());

উপরের ফলস্বরূপ সমস্ত প্যারেন্ট স্তরের পরীক্ষা না করেই আমার কাছে কোনও রুম অবজেক্ট বা নাল হয়ে যায়।

আপনি উপরেরটি সম্পর্কে কী ভাবেন? আমি কি সমস্যাযুক্ত প্যাটার্ন তৈরি করছি? আপনার মতে এটি করার আরও ভাল উপায় আছে কি?


1
আপনি স্পষ্টত জাভা 8 ব্যবহার করছেন, আমি কি আপনাকে পরামর্শ দিচ্ছি যে আপনার java.util.Optionalঅনুপস্থিত ডেটা উপস্থাপনের জন্য নাল পরিবর্তে আপনার অ্যাপ্লিকেশনটি পুনরায় ডিজাইনের বিবেচনা করবেন ? এটি আপনার বর্ণনার ক্ষেত্রে এবং যে ক্ষেত্রে কেবল শৃঙ্খলের শেষে ব্যর্থতার শর্তটি ফিরিয়ে দেওয়ার পরিবর্তে আপনি ডিফল্ট ডেটা
সহ চালনা

আমি মনে করি আপনি মূলত Option(বা Maybe) মোনাদটি পুনরায় আবিষ্কার করেছেন :)
আন্দ্রেস এফ।

টি বা নাল এর পরিবর্তে ptionচ্ছিক ফিরিয়ে দেওয়া সম্ভব হতে পারে: আপনি সরাসরি orElse () পদ্ধতিটি ব্যবহার করতে পারেন। 18 মাস পরে, তবে কাউকে সাহায্য করতে পারে।
বেনজ 2'18

এই পোস্টে অবৈধভাবে অন্য পদ্ধতির কথা উল্লেখ করা হয়েছে , অবৈধভাবে একটি কুলডজে নামে একটি গ্রন্থাগার ব্যবহার করছেন যা খুব আকর্ষণীয় বাক্য গঠন করেছে
বেনজ

উত্তর:


13

আপনার সমাধান খুব স্মার্ট। আমি যে সমস্যাটি দেখছি তা হ'ল আপনি কেন জানেন না কেন null? বাড়িটির কোনও ঘর ছিল না বলে? শহরে কোনও বাড়িঘর ছিল না কেন? দেশের কোন শহর ছিল না বলে? null1 এবং এর চেয়েও বেশি পজিশনে ঘর থাকা সত্ত্বেও কোনও ত্রুটির কারণে সংগ্রহের 0 পজিশনে থাকার কারণে এটি ছিল ?

আপনি যদি ক্লাসটির এক্সটেনসিবি ব্যবহার করেন তবে NonPEআপনার গুরুতর ডিবাগিং সমস্যা হবে। আমি মনে করি nullযে গভীর চূড়ান্ত কোনও আড়াল হতে পারে এমন নীরবে চুপটি করে পাওয়ার চেয়ে চেইনটি কোথায় ঠিক ভেঙে গেছে তা আরও ভাল ।

এছাড়াও এই লঙ্ঘন Demeter আইন : country.getTown().getHouses().get(0).getLivingRoom()। প্রায়শই না করা, কিছু ভাল নীতি লঙ্ঘন করা আপনাকে এ জাতীয় নীতি লঙ্ঘনের ফলে সৃষ্ট সমস্যা সমাধানের জন্য অপ্রথাবাদী সমাধানগুলি প্রয়োগ করতে হবে।

আমার সুপারিশটি হ'ল আপনি এটিকে সতর্কতার সাথে ব্যবহার করুন এবং ডিজাইনের ত্রুটিটি সমাধান করার চেষ্টা করুন যা আপনাকে ট্রেনের রেক অ্যান্টিপ্যাটার্ন (যাতে আপনাকে NonPEসর্বত্র ব্যবহার করতে হবে না ) করতে হয়। অন্যথায় আপনার কাছে বাগগুলি থাকতে পারে যা সনাক্ত করা শক্ত।


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

সাধারণভাবে, Optionমোনাড ব্যবহার করার সময় , আপনি চিন্তিত করবেন না যে চেইনে অনুপস্থিত মানটি কোথায়। আপনি যখন এটি সম্পর্কে যত্নশীল হন, আপনি সম্ভবত কোনও ভিন্ন ধরণের ব্যবহার করতে চান Either
আন্দ্রেস এফ।

ওপির দৃষ্টিভঙ্গি সি # 6 এর ?.এবং ?[]অপারেটরগুলির মতো। আপনি যখন এই জাতীয় জিনিসটি ব্যবহার করতে চান তার একটি উদাহরণ হায়ারার্কিকাল সার্ভার-সাইড সেটিংস। var shouldDoThing = settings?.a?.b?.c ?? defaultSetting;কে কেন যত্ন করে যে এর কোনও অংশ শূন্য ছিল কেন? সম্ভবত আপনি সেটিংস আনতে পারেননি। হতে পারে আপনি সেটিংসের একটি বিভাগ অপসারণ করার সিদ্ধান্ত নিয়েছেন। যাইহোক, আপনি কখনই সার্ভারের সেটিংস পাওয়ার বিষয়ে সত্যই নির্ভর করতে পারবেন না, তাই একটি ডিফল্ট সাধারণত ভাল ধারণা এবং আপনি যখনই আসেন না কেন এটি প্রকৃত সেটিংটি কেন না পেতে পারলে আপনি তার যত্ন নেওয়ার সম্ভাবনা কম when ।
ক্রিস

এখন আমি বলছি না যে ডিফল্টগুলির স্থানীয়করণ এবং সাধারণ অ্যাক্সেসের মাধ্যমে আপনি যে মানটি চান তা ফিরে পাওয়ার চেয়ে কঠোরতর বা খারাপ settings.a.b.c। তারপরে আবার এটি একক বিচ্ছিন্ন উদাহরণ।
ক্রিস

10

ধারণাটি ঠিক আছে, বাস্তবে খুব ভাল। যেহেতু জাভা 8 Optionalপ্রকারগুলি বিদ্যমান, তাই জাভা ptionচ্ছিক ধরণের একটি বিস্তারিত ব্যাখ্যা পাওয়া যাবে । আপনি যা পোস্ট করেছেন তার একটি উদাহরণ

Optional.ofNullable(country)
    .map(Country::getTown)
    .map(Town::Houses);

এবং আরও।


1
হ্যাঁ আমি জাভা 8 এবং পেয়ারা উভয় থেকেই ptionচ্ছিক ক্লাস সম্পর্কে অবগত ছিলাম এবং সেগুলি সত্যই কার্যকর। তবে আপনি কেবল কোনও বস্তু আনতে পারবেন না কারণ আপনি সাধারণত কোডটি পড়া আরও কঠিন এবং কিছুটা কম পারফরম্যান্ট করে তোলেন। কিন্তু বিপরীতটি হ'ল veryচ্ছিক শ্রেণি সরবরাহ করে এমন অনেকগুলি দরকারী অপারেটর রয়েছে।
ইউরিগ জোন্স

3
@ ইউরিগজোনস আমি মনে করি না কোডটি কম পারফরম্যান্ট হয়ে গেছে। দর্শকের চোখে পঠনযোগ্যতা, তবে আমি যুক্তি দিই যে Optionalদুজনের আরও পঠিত সমাধান হ'ল কেবল কারণ - আপনার প্রস্তাবের বিপরীতে - এটি খুব সাধারণ বুদ্ধিমান। এটি আপনার চেয়ে আরও সংক্ষিপ্ত!
আন্দ্রেস এফ।

0

আপনার পদ্ধতিটি তার উদ্দেশ্যযুক্ত উদ্দেশ্যে যথেষ্ট ভাল কাজ করে, যদিও nullআপনি NullPointerExceptionখারাপ ডিজাইনের মতো শব্দ পেয়ে ফিরে আসছেন ।

nullযখন আপনি কোনও কিছু উপস্থাপন করেন বা বিশেষ অর্থ রাখেন তখন কেবল সেগুলি পাস করতে পারলে সেগুলি এড়িয়ে চলার চেষ্টা করুন এবং যখন তারা কোনও কিছু উপস্থাপন / বোঝায় তখনই তাদের ফিরিয়ে দিন - অন্যথায় আপনি একটি নিক্ষেপ করা উচিত NullPointerException। এটি বাগ এবং বিভ্রান্তি এড়ায়। যদি একটি Objectনা হয় তবে nullএকটি NullPointerনিক্ষেপ করা উচিত। যদি কোনও বস্তু হতে পারে nullতবে কোনওটি যখন পাস করা হবে তখন কিছুই ভুল হবে না Otherwise অন্যথায় আপনার পদ্ধতিটি উপরে কাজ করে।


0

আমি আপনার ব্যথা অনুভব করতে পারি, তবে প্রস্তাবিত সমাধানটি একটি খারাপ ধারণা।

  • যদি প্রাপ্তিদের মধ্যে কেউ অন্য কোনও কারণে এনপিই ছুড়ে দেয় তবে আপনি এটিকে এড়িয়ে যাবেন।
  • ভয়ঙ্কর কোডে পরিণত হওয়ার জন্য সেই অভ্যন্তরের ল্যাম্বডায় ঝুঁকি রয়েছে। উদাহরণস্বরূপ, শহরে বাড়িগুলি নেই এমন সময়ে যদি কোনও বিশেষ ধ্রুবক ফিরিয়ে আনার কোনও নতুন প্রয়োজনীয়তা থাকে, তবে একটি অলস প্রোগ্রামার ল্যামদা প্রসারিত করতে পারে এবং সমস্ত কিছু আবৃত রেখে NoNPE.get
  • ইতিমধ্যে উল্লিখিত হিসাবে, Optional.mapআপনি কি খুঁজছেন হয়।
  • নুলপয়েন্টারএক্সসেপশনটির একটি নতুন উদাহরণ তৈরি করার দণ্ডটি প্রায়শই তাৎপর্যপূর্ণ। এটি অনেকগুলি মাইক্রোসেকেন্ড রয়েছে, বিশেষত আপনার কল স্ট্যাকটি আরও বড় হচ্ছে। আপনার ইউটিলিটিটি কোথায় ব্যবহৃত হবে তা নির্ধারণ করা শক্ত।

পার্শ্ব নোট হিসাবে, NoNPEInterfaceএর একটি সদৃশ java.util.function.Supplier

কিছু ক্ষেত্রে আপনি একটি এক্সপ্রেশন মূল্যায়ন ব্যবহারগুলি বিবেচনা করতে পারেন যা অনেকগুলি ফ্রেমওয়ার্কে উপস্থিত রয়েছে (উদাহরণস্বরূপ: EL, Spel):

evaluateProperty(country, "town.houses[0].livingRoom")

ওয়েব পৃষ্ঠার টেম্পলেটগুলির জন্য ঠিক আছে, তবে সাধারণত বিকাশ করতে ধীর হয় (কোনও সংকলনের সময় পরীক্ষা করা হয় না) এবং চালাতে ধীর হয়।
কেভিন ক্লিন
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.