ইক্যুয়ালিটি অপারেটর সি ++ 20 তে একটি কাস্টম স্পেসশিপ অপারেটর বাস্তবায়নের জন্য সংজ্ঞায়িত হয় না


51

আমি <=>সি ++ 20 তে নতুন স্পেসশিপ অপারেটরের সাথে এক অদ্ভুত আচরণে চলে আসছি । আমি ভিজুয়াল স্টুডিও 2019 সংকলকটি ব্যবহার করছি /std:c++latest

এই কোডটি প্রত্যাশিত হিসাবে জরিমানা সংকলন করেছে:

#include <compare>

struct X
{
    int Dummy = 0;
    auto operator<=>(const X&) const = default; // Default implementation
};

int main()
{
    X a, b;

    a == b; // OK!

    return 0;
}

তবে, আমি যদি এইটিতে এক্স পরিবর্তন করি :

struct X
{
    int Dummy = 0;
    auto operator<=>(const X& other) const
    {
        return Dummy <=> other.Dummy;
    }
};

আমি নিম্নলিখিত সংকলক ত্রুটি পেয়েছি:

error C2676: binary '==': 'X' does not define this operator or a conversion to a type acceptable to the predefined operator

আমি ঝাঁকুনির উপরও এটি চেষ্টা করেছি এবং আমিও একইরকম আচরণ পেয়েছি।

আমি কেন ডিফল্ট বাস্তবায়ন operator==সঠিকভাবে উত্পন্ন করে তার কিছু ব্যাখ্যা প্রশংসা করব , কিন্তু কাস্টমটি এটি করে না।

উত্তর:


50

এটি নকশা দ্বারা।

[class.compare.default] (জোর আমার)

3 যদি শ্রেণি সংজ্ঞাটি কোনও == অপারেটর ফাংশন স্পষ্টভাবে ঘোষণা করে না , তবে ত্রিমুখী তুলনামূলক অপারেটর ক্রিয়াকলাপটিকে স্পষ্টভাবে ঘোষণা করে, একটি অপারেটর ফাংশনটি ত্রি-উপা তুলনা অপারেটর ফাংশনের ==মতো একই অ্যাক্সেসের সাথে স্পষ্টভাবে ঘোষণা করা হয় । দশম ==শ্রেণির জন্য স্পষ্টভাবে ঘোষিত অপারেটর একটি ইনলাইন সদস্য এবং এক্স এর সংজ্ঞায় ডিফল্ট হিসাবে সংজ্ঞায়িত হয় is

কেবলমাত্র একটি ডিফল্ট <=>একটি সংশ্লেষিত ==অস্তিত্বের অনুমতি দেয় । যুক্তিটি হ'ল পছন্দ মতো ক্লাসগুলি std::vectorডিফল্ট ব্যবহার করতে পারে না <=>। উপরন্তু, ব্যবহার <=>জন্য ==ভেক্টর তুলনা করতে সবচেয়ে কার্যকর উপায় নয়। <=>অবশ্যই যথাযথ অর্ডারিং দিতে হবে, তবে ==প্রথমে মাপের তুলনা করে তাড়াতাড়ি জামিন দিতে পারে।

যদি কোনও শ্রেণি তার ত্রি-উপায়ে তুলনায় বিশেষ কিছু করে, সম্ভবত এর মধ্যে এটিতে বিশেষ কিছু করা দরকার ==। সুতরাং, অ-বুদ্ধিমান ডিফল্ট তৈরির পরিবর্তে, ভাষা প্রোগ্রামার পর্যন্ত ছেড়ে দেয়।


4
স্পেসশিপ বগি না হলে এটি অবশ্যই বোধগম্য। সম্ভাব্য গুরুতরভাবে অদক্ষ হলেও ...
হস্তান্তরকারী

1
@ প্রতিলিপি - সংবেদনশীলতা বিষয়গত। কেউ কেউ বুদ্ধিমান না হওয়ার জন্য নীরবে উত্পন্ন অদক্ষ বাস্তবায়ন বলবেন।
গল্পগ্রাহক - আনস্ল্যান্ডার মনিকা

45

এই বৈশিষ্ট্যের মানককরণের সময়, সিদ্ধান্ত নেওয়া হয়েছিল যে সাম্যতা এবং আদেশকে যৌক্তিকভাবে পৃথক করা উচিত। যেমন, সাম্য পরীক্ষার ব্যবহারগুলি ( ==এবং !=) কখনই প্রার্থনা করবে নাoperator<=> । তবে এটি উভয়কে একক ঘোষণার মাধ্যমে ডিফল্ট করতে সক্ষম হিসাবে কার্যকর হিসাবে দেখা গেছে। সুতরাং আপনি যদি ডিফল্ট হন তবে operator<=>সিদ্ধান্ত নেওয়া হয়েছিল যে আপনিও ডিফল্ট বলতে চেয়েছিলেন operator==(যদি আপনি এটি পরে সংজ্ঞায়িত না করেন বা এর আগে সংজ্ঞা না দিয়ে থাকেন)।

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

তবে স্ট্রিংয়ের সমতা পরীক্ষার একটি শর্ট সার্কিট রয়েছে। যদি দুটি স্ট্রিং সমান দৈর্ঘ্যের না হয়, তবে চরিত্র-ভিত্তিক তুলনা মোটেও লাভ করার উপায় নেই; তারা সমান নয়। সুতরাং যদি কেউ সাম্য পরীক্ষা করে নিচ্ছেন, আপনি যদি এটির শর্ট সার্কিট করতে পারেন তবে আপনি এটি দীর্ঘ-রূপে করতে চান না।

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


5
এটি গৃহীত উত্তরের চেয়ে অনেক বেশি ভাল ব্যাখ্যা
মেমো

17

অন্যান্য উত্তরগুলি ভাষাটি কেন এমন হয় তা সত্যিই ভালভাবে ব্যাখ্যা করে। আমি কেবল এটি যুক্ত করতে চেয়েছিলাম যদি এটি সুস্পষ্ট না হয় তবে অবশ্যই কোনও ব্যবহারকারীকে operator<=>ডিফল্ট সরবরাহ করা সম্ভব operator==। আপনাকে কেবল স্পষ্টভাবে ডিফল্ট লিখতে হবে operator==:

struct X
{
    int Dummy = 0;
    auto operator<=>(const X& other) const
    {
        return Dummy <=> other.Dummy;
    }
    bool operator==(const X& other) const = default;
};
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.