গেটর এবং সেটার?


203

আমি কোনও পিএইচপি বিকাশকারী নই, তাই আমি ভাবছি যে পিএইচপি তে ব্যক্তিগত ক্ষেত্রগুলি (আমার পছন্দ মতো) সাথে খাঁটি ওওপি স্টাইলে সুস্পষ্ট গেটার / সেটটার ব্যবহার করা বেশি জনপ্রিয় কিনা:

class MyClass {
    private $firstField;
    private $secondField;

    public function getFirstField() {
        return $this->firstField;
    }
    public function setFirstField($x) {
        $this->firstField = $x;
    }
    public function getSecondField() {
        return $this->secondField;
    }
    public function setSecondField($x) {
        $this->secondField = $x;
    }
}

বা কেবল সর্বজনীন ক্ষেত্র:

class MyClass {
    public $firstField;
    public $secondField;
}

ধন্যবাদ


7
উত্তরগুলি থেকে কিছু কোড চেষ্টা করার পরে আপনি প্রশ্নটিতে যে কোডটি ব্যবহার করছেন তা ব্যবহার করেছি। কত দুঃখজনক :-(
১id

9
পিএইচপিস্টর্ম ... জেনারেটর> সিটার এবং সেটটারগুলি। == জয়
ডেভডনকি

@ ডেভডনকি মোটেও জয় নয় কাঠামোগত ডেটা ধরে রাখতে, পরিবর্তে অ্যারে ব্যবহার করুন @: চিহ্নিত করুন এটি কীসের জন্য বা কীসের জন্য তা নয়। গেটার্স এবং সেটারগুলি
কুবু 2

উত্তর:


222

আপনি পিএইচপি যাদু পদ্ধতি __get এবং ব্যবহার করতে পারেন __set

<?php
class MyClass {
  private $firstField;
  private $secondField;

  public function __get($property) {
    if (property_exists($this, $property)) {
      return $this->$property;
    }
  }

  public function __set($property, $value) {
    if (property_exists($this, $property)) {
      $this->$property = $value;
    }

    return $this;
  }
}
?>

15
আমি মনে করি আপনি বোঝাতে চেয়েছিলেন __getএবং __set। দুটি নয় আন্ডারস্কোর, একটি নয়। এখানে পৃষ্ঠার ডান অংশের সরাসরি লিঙ্কটি রয়েছে: php.net/manual/en/… (সঠিক উত্তরের জন্য +1)
কম্পিউটারিশ

28
publicবৈধতা / স্যানিটেশন না থাকলে সম্পত্তিগুলির বিরুদ্ধে কী লাভ ?
কিংক্রাঞ্চ

7
@ কিিংক্রাঞ্চ, এটি কেবল একটি উদাহরণ। একটি শক্তিশালী সংস্থান জন্য একটি খুব চতুর উদাহরণ।
ডেভিস পিক্সোটো

10
এটি সত্যিই সেটার এবং গেটর নয়। সাধারণত আমি প্রতিটি সম্পত্তি গেটরের বিভিন্ন প্রয়োগ প্রয়োজন!
59-

79
দয়া করে করবেন না: যাদু পদ্ধতির সাহায্যে আপনি প্রায় প্রতিটি মানের-সম্পর্কিত বৈশিষ্ট্যগুলি অনেক আইডিইতে (এমনকি ভিআইএম) হারাবেন: স্বতঃ-সমাপ্তি, সুস্পষ্ট পিএইচপি উত্তরাধিকার, দ্রুত পিএইচপি ব্যাখ্যা এবং ব্যবহারযোগ্য পিএইচপিডোক জেনারেশন এবং আউটপুট। cf. stackoverflow.com/a/6184893/490589
রোনান

113

কেন গেটার এবং সেটটার ব্যবহার করবেন?

  1. স্কেলিবিলিটি : একটি প্রকল্প কোডের সমস্ত ভেরি অ্যাসাইনমেন্ট অনুসন্ধান করার চেয়ে এটি আরও সহজ রিফ্যাক্টর।
  2. ডিবাগিং : আপনি সেটার এবং গিটারগুলিতে ব্রেকপয়েন্ট রাখতে পারেন।
  3. ক্লিনার : ম্যাজিক ফাংশনগুলি কম রাইটিংয়ের জন্য ভাল সমাধান নয়, আপনার আইডিই কোডটি সুপারিশ করবে না। দ্রুত-লিখনকারীদের জন্য আরও ভাল ব্যবহারের টেম্পলেট

সরাসরি অ্যাসাইনমেন্ট এবং গেটার / সেটার্স


7
আপনি যদি @ প্রপার্টি ব্যবহার করেন তবে আপনার আইডিই কোডটি প্রস্তাব করবে (পিএইচপিস্টর্ম 7 দিয়ে পরীক্ষিত)
অ্যালেক্স

41

গুগল ইতিমধ্যে পিএইচপি অনুকূলিতকরণ সম্পর্কিত একটি গাইড প্রকাশ করেছে এবং উপসংহারটি ছিল:

কোনও গেটর এবং সেটার অপ্টিমাইজিং পিএইচপি নেই

এবং না, আপনার অবশ্যই যাদু পদ্ধতি ব্যবহার করা উচিত নয় । পিএইচপি-র জন্য, ম্যাজিক পদ্ধতিটি খারাপ। কেন?

  1. তাদের ডিবাগ করা শক্ত।
  2. নেতিবাচক কর্মক্ষমতা প্রভাব আছে।
  3. তাদের আরও কোড লেখার প্রয়োজন।

পিএইচপি জাভা, সি ++ বা সি # নয়। পিএইচপি আলাদা এবং বিভিন্ন ভূমিকায় অভিনয় করে।


10
আমি এই ধারণার সাথে একমত হই; যে $dog->name = 'fido'তুলনায় ভাল $dog->setName('fido')। যখন আসলে (ক সম্পত্তি mutating উদা: $dog->increaseAge(1)। আমি পদ্ধতি প্রয়োজনীয় বৈধতা এবং mutates যে সম্পত্তি আছে আউট নির্মাণ করতে পারেন কিন্তু সমস্ত ক্রিয়া সত্যিই যে অর্থে পরিব্যক্তি প্রয়োজন।
চার্লি Schliesser

11
নিবন্ধ নেই "বলে না ", এটা বলে 'সাদাসিধা setters এবং getters' আছে।
ব্রেট স্যান্টোর

1
এটি পুনরুদ্ধার করা হয়েছে: web.archive.org/web/20140625191431/https://…

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

3
এটি বলার মতো যে ইনলাইন স্টাইলিং ভাল। অবশ্যই পারফরম্যান্স ভাল, তবে এটি কি আরও ভাল কোড? আমি জানতাম না গুগল ইঞ্জিনিয়াররা পিএইচপি ব্যবহার করুন যাইহোক
ক্লাদিউ ক্রেঙ্গা

13

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

পিএইচপি-তে, এটি কাজ করে:

class Foo {
   public $bar; // should be an integer
}
$foo = new Foo;
$foo->bar = "string";

জাভাতে, এটি হয় না:

class Foo {
   public int bar;
}
Foo myFoo = new Foo();
myFoo.bar = "string"; // error

যাদু পদ্ধতিগুলি ( __getএবং __set) ব্যবহার করাও কাজ করে, তবে কেবলমাত্র এমন সুযোগে অ্যাক্সেস করা যখন বর্তমান সুযোগের চেয়ে কম দৃশ্যমান থাকে access এটি সঠিকভাবে ব্যবহার না করা হলে ডিবাগ করার চেষ্টা করার সময় সহজেই আপনাকে মাথা ব্যাথা দিতে পারে।


7
গেটারস এবং সেটার এনক্যাপসুলেশন আনবে না। এনক্যাপসুলেশন == অবজেক্টগুলি এগুলি বাইরে দেওয়ার পরিবর্তে নিজস্ব ডেটা দিয়ে কিছু করে। গেটার্স এবং সেটাররা পিএইচপি এর মতো গতিময় টাইপ করা ভাষায় টাইপ প্রয়োগের জন্য কোনও সরঞ্জাম নয়।
smentek

14
@ সেমেনটেক: এনক্যাপসুলেশন আসলে কী তার কমপক্ষে অর্ধেক আপনি অনুপস্থিত।
নেটকোডার

2
যে কেউ খুঁজছেন তার এটির আপডেট হিসাবে, পিএইচপি 7.4 টাইপ করা সম্পত্তি সমর্থন নিয়ে আসবে। সুতরাং আপনি প্রথম উদাহরণে এটি $barহিসাবে ঘোষণা করতে পারেন int: wiki.php.net/rfc/typed_properties_v2
কেভিন

7

যদি আপনি __call ফাংশনটি ব্যবহার করতে পছন্দ করেন তবে আপনি এই পদ্ধতিটি ব্যবহার করতে পারেন। এটি সঙ্গে কাজ করে

  • গেট => $this->property()
  • সেট => $this->property($value)
  • গেট => $this->getProperty()
  • সেট => $this->setProperty($value)

kalsdas

public function __call($name, $arguments) {

    //Getting and setting with $this->property($optional);

    if (property_exists(get_class($this), $name)) {


        //Always set the value if a parameter is passed
        if (count($arguments) == 1) {
            /* set */
            $this->$name = $arguments[0];
        } else if (count($arguments) > 1) {
            throw new \Exception("Setter for $name only accepts one parameter.");
        }

        //Always return the value (Even on the set)
        return $this->$name;
    }

    //If it doesn't chech if its a normal old type setter ot getter
    //Getting and setting with $this->getProperty($optional);
    //Getting and setting with $this->setProperty($optional);
    $prefix = substr($name, 0, 3);
    $property = strtolower($name[3]) . substr($name, 4);
    switch ($prefix) {
        case 'get':
            return $this->$property;
            break;
        case 'set':
            //Always set the value if a parameter is passed
            if (count($arguments) != 1) {
                throw new \Exception("Setter for $name requires exactly one parameter.");
            }
            $this->$property = $arguments[0];
            //Always return the value (Even on the set)
            return $this->$name;
        default:
            throw new \Exception("Property $name doesn't exist.");
            break;
    }
}

2
@ krzysztof-przygoda: এই "ম্যাজিক পদ্ধতি" সর্বদা দাম নিয়ে আসে। তাদের পুনরাবৃত্তি ব্যবহার করতে হবে property_exists(get_class($this), $name)এবং পুনরাবৃত্তিগুলি ধীর। এটি ক্যাশে করার মাধ্যমে প্রশমিত করার জন্য একটি উপায় আছে তবে এটি হাত দিয়ে গেটার এবং সেটটার তৈরি করার চেয়ে ধীর হতে চলেছে। আমি কেবল এটি বিকল্প হিসাবে লিখেছি। আমি আসলে "ম্যাজিক পদ্ধতি" ব্যবহার করার পরামর্শ দিই না। গেটার্স এবং সেটটারগুলি তৈরি করার অতিরিক্ত সময় সাধারণত তুচ্ছ।
জে-রউজ

7

এখানে ইতিমধ্যে দুর্দান্ত এবং সম্মানিত উত্তরগুলি ছাড়াও, আমি পিএইচপিগুলিতে কোনও সেটার / গেটার না থাকায় প্রসারিত করতে চাই।

পিএইচপি-তে গিটার এবং সেটার সিনট্যাক্স নেইডেভ দ্বারা নির্দেশিত হিসাবে এটি "হুকিং" এবং সম্পত্তি অনুসন্ধান প্রক্রিয়াটিকে ওভাররাইড করার অনুমতি দেওয়ারজন্য সাবক্ল্যাসড বা ম্যাজিক পদ্ধতি সরবরাহ করে।

যাদু আমাদের অলস প্রোগ্রামারদের এমন সময়ে কম কোডের সাথে আরও বেশি কাজ করার অনুমতি দেয় যা আমরা সক্রিয়ভাবে কোনও প্রকল্পে নিযুক্ত থাকি এবং এটি ঘনিষ্ঠভাবে জানি তবে সাধারণত পাঠযোগ্যতার ব্যয়ে।

পারফরম্যান্স প্রতিটি অপ্রয়োজনীয় ফাংশন, যা পিএইচপি-তে একটি গিটার / সেটার-জাতীয় কোড-আর্কিটেকচার জোর করে ফলাফল, অনুরোধের পরে তার নিজস্ব মেমরি স্ট্যাক-ফ্রেম জড়িত করে এবং সিপিইউ চক্র নষ্ট করে।

পঠনযোগ্যতা: কোডবেসে ব্লুটিং কোড-লাইনগুলি অন্তর্ভুক্ত রয়েছে, যা কোড-নেভিগেশনকে বেশি এলওসি হিসাবে প্রভাবিত করে যার অর্থ আরও বেশি স্ক্রোলিং ,.

পছন্দ: ব্যক্তিগতভাবে, আমার আঙ্গুলের নিয়ম হিসাবে, আমি স্থায়ী কোড বিশ্লেষণের ব্যর্থতাটিকে যাদুর রাস্তায় নামতে না পারার লক্ষণ হিসাবে গ্রহণ করি যতক্ষণ না সুস্পষ্ট দীর্ঘমেয়াদী সুবিধাগুলি ততক্ষণে আমাকে ছাড়িয়ে যায়।

Fallacies:

একটি সাধারণ যুক্তি হ'ল পাঠযোগ্যতা। উদাহরণস্বরূপ যা $someobject->widthপড়ার চেয়ে সহজ $someobject->width()। তবে কোনও গ্রহের circumferenceবা widthযা ধারণা করা যেতে পারে তার বিপরীতে staticকোনও বস্তুর উদাহরণ যেমন $someobjectএকটি প্রস্থের ফাংশন প্রয়োজন, সম্ভবত অবজেক্টের উদাহরণের প্রস্থের একটি পরিমাপ নেয়।
অতএব পাঠযোগ্যতা বৃদ্ধি পায় মূলত দৃser় নামকরণ-স্কিমগুলির কারণে এবং কোনও প্রদত্ত সম্পত্তি-মূল্যকে আউটপুট করে ফাংশনটি লুকিয়ে রাখার দ্বারা নয়।

__get / __set ব্যবহার করে:

  • প্রাক-বৈধকরণ এবং সম্পত্তি মূল্য প্রাক-স্যানিটেশন

  • স্ট্রিং যেমন

    "
    some {mathsobj1->generatelatex} multi
    line text {mathsobj1->latexoutput}
    with lots of variables for {mathsobj1->generatelatex}
     some reason
    "

    এক্ষেত্রে generatelatex actionname + + methodname একটি নামকরণ স্কীম মেনে চলে যাবে

  • বিশেষ, সুস্পষ্ট কেস

    $dnastringobj->homeobox($one_rememberable_parameter)->gattaca->findrelated()
    $dnastringobj->homeobox($one_rememberable_parameter)->gttccaatttga->findrelated()

দ্রষ্টব্য: পিএইচপি গিটার / সেটার সিনট্যাক্স প্রয়োগ না করা বেছে নিয়েছে। আমি দাবি করছি না যে গেটার্স / সেটারগুলি সাধারণত খারাপ।


6
class MyClass {
    private $firstField;
    private $secondField;
    private $thirdField;

    public function __get( $name ) {
        if( method_exists( $this , $method = ( 'get' . ucfirst( $name  ) ) ) )
            return $this->$method();
        else
            throw new Exception( 'Can\'t get property ' . $name );
    }

    public function __set( $name , $value ) {
        if( method_exists( $this , $method = ( 'set' . ucfirst( $name  ) ) ) )
            return $this->$method( $value );
        else
            throw new Exception( 'Can\'t set property ' . $name );
    }

    public function __isset( $name )
    {
        return method_exists( $this , 'get' . ucfirst( $name  ) ) 
            || method_exists( $this , 'set' . ucfirst( $name  ) );
    }

    public function getFirstField() {
        return $this->firstField;
    }

    protected function setFirstField($x) {
        $this->firstField = $x;
    }

    private function getSecondField() {
        return $this->secondField;
    }
}

$obj = new MyClass();

echo $obj->firstField; // works
$obj->firstField = 'value'; // works

echo $obj->getFirstField(); // works
$obj->setFirstField( 'value' ); // not works, method is protected

echo $obj->secondField; // works
echo $obj->getSecondField(); // not works, method is private

$obj->secondField = 'value'; // not works, setter not exists

echo $obj->thirdField; // not works, property not exists

isset( $obj->firstField ); // returns true
isset( $obj->secondField ); // returns true
isset( $obj->thirdField ); // returns false

প্রস্তুত!


অনেক বেশি বয়লারপ্লেট। এই স্টাফটি প্রতিটি ক্লাসে রয়েছে তা কল্পনা করুন। আইএমও
এড়ান

আপনার উল্লিখিত একই কারণে পিএইচপি গেটার এবং সেটটারকে সমর্থন করে না। এই ধরণের যে কোনও বাস্তবায়ন গুরুতরভাবে সার্ভার-সাইড স্ক্রিপ্টের কার্যকারিতা প্রভাবিত করে।
joas

আমি মনে করি এটি 'প্রাইভেট' বৈশিষ্ট্যের বিপরীতে। আপনি এগুলি encapsulate, কিন্তু সরাসরি অ্যাক্সেস অনুমতি দেয়।
Koray Küpe

@ KorayKüpe কেবলমাত্র গ্রাহককে সংজ্ঞায়িত করা হলে। আমি এই এনকেপসুলেশনটি অনেক ব্যবহার করি (অনেক উন্নতি সহ) এবং এটি পুরোপুরি কার্যকর হয়। আপনি ক্লাসটি প্রসারিত করতে এবং সহজেই সমস্ত কোডে এটি ব্যবহার করতে পারেন।
জোস

5

ওয়েল, পিএইচপি যাদু পদ্ধতি আছে __get, __set, __isset& __unset, যা সবসময় একটি সূচনা। হায়রে যথাযথ (এটি পেয়েছেন?) ওও বৈশিষ্ট্যগুলি যাদু পদ্ধতির চেয়ে বেশি। পিএইচপি বাস্তবায়নের প্রধান সমস্যাটি হ'ল যাদু পদ্ধতিগুলি সমস্ত অ্যাক্সেস অযোগ্য বৈশিষ্ট্যের জন্য ডাকা হয় । যার অর্থ আপনার নিজের নিজেকে পুনরাবৃত্তি করতে হবে (উদাহরণস্বরূপ, সম্পত্তি_এক্সজিস্টদের কল করে): যখন নামটি আসলে আপনার সামগ্রীর সম্পত্তি কিনা তা নির্ধারণ করে । এবং যদি আপনার সমস্ত ক্লাসগুলি ইহাতে উত্তরাধিকার সূত্রে না পাওয়া যায় তবে আপনি বেস ক্লাসের সাথে এই সাধারণ সমস্যাটি সত্যিই সমাধান করতে পারবেন না। ClassWithProperties, যেহেতু PHP এর একাধিক উত্তরাধিকার নেই ance

বিপরীতে, পাইথন নতুন স্টাইলের ক্লাসগুলি আপনাকে দেয় property()যা আপনাকে আপনার সমস্ত বৈশিষ্ট্য স্পষ্টভাবে সংজ্ঞায়িত করতে দেয়। সি # এর বিশেষ সিনট্যাক্স রয়েছে।

http://en.wikipedia.org/wiki/Property_(programming)


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

1
যথেষ্ট ফর্সা। কিন্তু পাইথন এবং সি # তে এই পুনরাবৃত্তি প্রয়োজন হয় না। আমি মনে করি এটি একটি শক্তি।
ইমানুয়েল ল্যান্ডহোম

4

আমি যাদু পদ্ধতি __call ব্যবহার করে একটি পরীক্ষা করেছি। আমার এটি পোস্ট করা উচিত কিনা তা নিশ্চিত নয় (কারণ "অন্যান্য উত্তর এবং মন্তব্যে সমস্ত" ম্যাজিক মেথড ব্যবহার করবেন না ") সতর্কতা থাকলেও আমি এটিকে এখানে রেখে দেব .. যদি কারওর পক্ষে এটি কার্যকর মনে হয়।


public function __call($_name, $_arguments){
    $action  = substr($_name, 0, 4);
    $varName = substr($_name, 4);

    if (isset($this->{$varName})){
        if ($action === "get_") return $this->{$varName};
        if ($action === "set_") $this->{$varName} = $_arguments[0];
    }
}

আপনার ক্লাসে কেবল সেই পদ্ধতিটি জুড়ুন, এখন আপনি টাইপ করতে পারেন:

class MyClass{
    private foo = "bar";
    private bom = "bim";
    // ...
    // public function __call(){ ... }
    // ...
}
$C = new MyClass();

// as getter
$C->get_foo(); // return "bar"
$C->get_bom(); // return "bim"

// as setter
$C->set_foo("abc"); // set "abc" as new value of foo
$C->set_bom("zam"); // set "zam" as new value of bom


এইভাবে আপনি যদি আপনার শ্রেণীর সমস্ত কিছু বিদ্যমান থাকে তা সেট / সেট করতে পারেন, যদি আপনার কেবলমাত্র কয়েকটি নির্দিষ্ট উপাদানের প্রয়োজন হয় তবে আপনি ফিল্টার হিসাবে "শ্বেতলিস্ট" ব্যবহার করতে পারেন।

উদাহরণ:

private $callWhiteList = array(
    "foo" => "foo",
    "fee" => "fee",
    // ...
);

public function __call($_name, $_arguments){
    $action  = substr($_name, 0, 4);
    $varName = $this->callWhiteList[substr($_name, 4)];

    if (!is_null($varName) && isset($this->{$varName})){
        if ($action === "get_") return $this->{$varName};
        if ($action === "set_") $this->{$varName} = $_arguments[0];
    }
}

এখন আপনি কেবল "ফু" এবং "ফি" পেতে / সেট করতে পারবেন।
আপনার বারগুলিতে অ্যাক্সেসের জন্য কাস্টম নামগুলি নির্ধারণ করতে আপনি সেই "শ্বেত তালিকা" ব্যবহার করতে পারেন।
উদাহরণ স্বরূপ,

private $callWhiteList = array(
    "myfoo" => "foo",
    "zim" => "bom",
    // ...
);

সেই তালিকার সাহায্যে আপনি এখন টাইপ করতে পারেন:

class MyClass{
    private foo = "bar";
    private bom = "bim";
    // ...
    // private $callWhiteList = array( ... )
    // public function __call(){ ... }
    // ...
}
$C = new MyClass();

// as getter
$C->get_myfoo(); // return "bar"
$C->get_zim(); // return "bim"

// as setter
$C->set_myfoo("abc"); // set "abc" as new value of foo
$C->set_zim("zam"); // set "zam" as new value of bom




এখানেই শেষ.


দস্তাবেজ: __call () একটি অবজেক্ট প্রসঙ্গে অ্যাক্সেসযোগ্য পদ্ধতিতে অনুরোধ করার সময় ট্রিগার করা হয়।


এই সমস্ত "যাদু" সমাধানগুলির সাথে সমস্যাটি হ'ল তারা এই যাদু পদ্ধতিগুলি কেবল সেখানে থাকার কারণে ব্যবহার করে এবং তারা দরকারী কারণ জিজ্ঞাসা করা সমস্যাটি একটি সাধারণ, জেনেরিক। জেনেরিক সমস্যার এই স্তরটি ছেড়ে যাওয়ার পরে, আপনি নির্দিষ্ট প্রয়োজনীয় প্রয়োজনীয়তার মুখোমুখি হবেন যা একটি সাধারণ ম্যাজিক পদ্ধতি দ্বারা সমাধান করা যায় না, তবে খুব জটিল ম্যাজিক পদ্ধতি - বা স্বতন্ত্র, কোডেড সেটার এবং গেটারগুলির প্রয়োজন হবে।
সেভেন

2

অন্যান্য পরামর্শগুলি পড়ার পরে, আমি এটি বলতে আগ্রহী:

জেনেরিক নিয়ম হিসাবে , আপনি সর্বদা সমস্ত বৈশিষ্ট্যগুলির জন্য সেটটারগুলি নির্দিষ্ট করে না , বিশেষত "অভ্যন্তরীণ" বেশী (সেমোফোরস, অভ্যন্তরীণ পতাকাগুলি ...)। কেবলমাত্র পঠনযোগ্য বৈশিষ্ট্যগুলিতে সেটটার থাকবে না, অবশ্যই, তাই কিছু সংখ্যায় কেবল গেটর থাকবে; এখানেই __get () কোড সঙ্কুচিত করতে আসে:

  • যাবতীয় সম্পত্তি হিসাবে একটি __get () (যাদুকর গ্লোবাল getters) সংজ্ঞায়িত করুন,
  • তাদের অ্যারে তে গ্রুপ করুন:
    • তারা সাধারণ বৈশিষ্ট্যগুলি ভাগ করে নেবে: আর্থিক মানগুলি সঠিকভাবে ফর্ম্যাটে আসে / নির্দিষ্ট লেআউটে (আইএসও, মার্কিন, ইনটেল।), ইত্যাদি তারিখগুলি উপস্থিত হতে পারে etc.
    • কোডটি নিজেই যাচাই করতে পারে যে কেবল বিদ্যমান এবং অনুমতিপ্রাপ্ত বৈশিষ্ট্যগুলি এই magন্দ্রজালিক পদ্ধতি ব্যবহার করে পড়া হচ্ছে।
    • যখনই আপনাকে নতুন নতুন অনুরূপ সম্পত্তি তৈরি করতে হবে, কেবল এটি ঘোষণা করুন এবং এর নামটি যথাযথ অ্যারেতে যুক্ত করুন এবং এটি হয়ে গেছে। কোনও নতুন গেটার সংজ্ঞায়নের চেয়ে দ্রুততর উপায় , সম্ভবত কিছু ক্লাস কোডের সাথে পুনরায় পুনরায় পুনরায় পাঠ করা কোডের কয়েকটি লাইন রয়েছে।

হ্যাঁ! আমরা এটি করার জন্য একটি ব্যক্তিগত পদ্ধতিও লিখতে পারি, তবে তারপরে আবারও আমাদের কাছে অনেকগুলি পদ্ধতি ঘোষিত হবে (++ মেমরি) যা অন্যটিকে ডেকে আনে, সর্বদা একই, পদ্ধতি। এগুলি সমস্ত শাসনের জন্য কেন একটি একক পদ্ধতি লিখবেন না ...? [হাঁ! পাং একেবারে উদ্দেশ্য! :)]

ম্যাজিক সেটারগুলি নির্দিষ্ট বৈশিষ্ট্যগুলিতে কেবলমাত্র প্রতিক্রিয়া জানাতে পারে, তাই সমস্ত তারিখের ধরণের বৈশিষ্ট্যগুলি কেবল একটি পদ্ধতিতে অবৈধ মানগুলির বিরুদ্ধে স্ক্রিন করা যায়। যদি তারিখের ধরণের বৈশিষ্ট্যগুলি একটি অ্যারেতে তালিকাভুক্ত করা হত তবে তাদের সেটারগুলি সহজেই সংজ্ঞায়িত করা যায়। অবশ্যই একটি উদাহরণ অবশ্যই। উপায় অনেক অনেক আছে।

পঠনযোগ্যতা সম্পর্কে ... ভাল ... এটি অন্য বিতর্ক: আমি কোনও আইডিই ব্যবহারে আবদ্ধ হতে পছন্দ করি না (আসলে, আমি সেগুলি ব্যবহার করি না, তারা আমাকে কীভাবে বলবে (এবং আমাকে জোর করে ) কীভাবে করতে হয় লিখুন ... এবং "সৌন্দর্য" কোডিং সম্পর্কে আমার পছন্দ আছে) likes আমি নামকরণের বিষয়ে সামঞ্জস্যপূর্ণ থাকি, তাই ctags এবং অন্যান্য কয়েকটি এইড ব্যবহার করা আমার পক্ষে যথেষ্ট ... যাইহোক: এই সমস্ত যাদু সেটারগুলি এবং কাজগুলি সম্পন্ন হয়ে গেলে আমি অন্যান্য সেটারগুলি লিখি যা খুব নির্দিষ্ট বা "বিশেষ" একটি __set () পদ্ধতিতে সাধারণীকরণ করুন। এবং এটি বৈশিষ্ট্য অর্জন এবং সেট করা সম্পর্কে আমার যা প্রয়োজন তা কভার করে। অবশ্যই: এখানে সবসময় একটি সাধারণ স্থল থাকে না, বা এমন কয়েকটি বৈশিষ্ট্য রয়েছে যা একটি যাদুকরী পদ্ধতিতে কোডিংয়ের ঝামেলার পক্ষে নয় এবং তারপরে এখনও পুরানো ভাল traditionalতিহ্যবাহী সেটার / গেটের জুড়ি রয়েছে।

প্রোগ্রামিং ভাষা ঠিক যে: মানব কৃত্রিম ভাষা। সুতরাং, তাদের প্রত্যেকের নিজস্ব স্বতন্ত্রতা বা অ্যাকসেন্ট, বাক্য গঠন এবং স্বাদ রয়েছে, তাই আমি জাভা বা সি # এর চেয়ে একই "অ্যাকসেন্ট" ব্যবহার করে রুবি বা পাইথন কোডটি লেখার ভান করব না বা সাদৃশ্য করার জন্য আমি কোনও জাভাস্ক্রিপ্ট বা পিএইচপি লিখব না would পার্ল বা এসকিউএল ... তারা যেভাবে ব্যবহার করতে চাইছে সেভাবে সেগুলি ব্যবহার করুন।


1

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


0

নেটবিন-কনভেনশনে সোর্সকোড তৈরির অনেকগুলি উপায় রয়েছে। এটা সুন্দর. এটি এমন সহজ চিন্তা করে তোলে === মিথ্যা। কেবল elতিহ্যবাহিনীটি ব্যবহার করুন, বিশেষত যদি আপনি নিশ্চিত হন না যে কোন বৈশিষ্ট্যটি এনপাসুলেটেড হওয়া উচিত এবং কোনটি নয়। আমি জানি, এটি একটি বোয়াই .... প্লা ... কোড, তবে ডিবাগিং-কাজগুলির জন্য এবং আরও অনেকে মনে করেন এটি সবচেয়ে ভাল, পরিষ্কার উপায়। কীভাবে সহজ গেটার্স এবং সেটটারগুলি তৈরি করা যায় তা আর্টস থোর্সেন্ডের সাথে বেশি সময় ব্যয় করবেন না। আপনি যদি ম্যাজিক ব্যবহার করেন তবে আপনি কিছু ডিজাইনের ধরণ যেমন ডেমিটার-বিধি ইত্যাদি বাস্তবায়ন করতে পারবেন না। নির্দিষ্ট পরিস্থিতিতে আপনি ম্যাজিক_ক্যালস বা ছোট, দ্রুত এবং স্পষ্ট সমাধানের জন্য ব্যবহার করতে পারেন। নিশ্চিত যে আপনি এইভাবে ডিজাইন-প্যাটারদের জন্য সমাধান তৈরি করতে পারেন তবে কেন আপনাকে আরও কঠিন করে তুলবেন।


0

বৈধকরণ + ফর্ম্যাট / ডেরাইভিং মান

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

উদাহরণস্বরূপ, নিম্নলিখিত জন্মগত তারিখ সহ সাধারণ শ্রেণি বিবেচনা করুন।

class BirthDate {

    private $birth_date;

    public function getBirthDate($format='Y-m-d') {
        //format $birth_date ...
        //$birth_date = ...
        return $birth_date;
    }

    public function setBirthDate($birth_date) {                   
        //if($birth_date is not valid) throw an exception ...          
        $this->birth_date = $birth_date;
    }

    public function getAge() {
        //calculate age ...
        return $age;
    }

    public function getDaysUntilBirthday() {
        //calculate days until birth days
        return $days;
    }
}

আপনি মানটি সেট করা হচ্ছে তা যাচাই করতে চাইবেন

  • একটি বৈধ তারিখ
  • ভবিষ্যতে না

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

আপনি একাধিক formatters যে একই সদস্য পরিবর্তনশীল অর্থাত কাজ জুড়তে চাইতে পারেন getAge()এবং getDaysUntilBirthday()এবং আপনি একটি কনফিগারযোগ্য বিন্যাস প্রয়োগ করতে চাইতে পারেন getBirthDate()লোকেল উপর নির্ভর করে। অতএব, আমি ধারাবাহিকভাবে getters মাধ্যমে মান অ্যাক্সেস পছন্দ হিসাবে মিশ উল্টোদিকে $date->getAge()সঙ্গে $date->birth_date

যখন আপনি বস্তুগুলি প্রসারিত করেন তখন গিটার এবং সেটারগুলিও কার্যকর। উদাহরণস্বরূপ, ধরুন আপনার অ্যাপ্লিকেশনটির কোনও কোনও জায়গায় 150+ বছরের জন্ম তারিখের অনুমতি দেওয়ার দরকার ছিল তবে অন্যত্র নয়। কোনও কোড পুনরাবৃত্তি না করেই সমস্যার সমাধান করার একটি উপায় হ'ল BirthDateঅবজেক্টটি প্রসারিত করা এবং সেটারে অতিরিক্ত বৈধতা দেওয়া।

class LivingBirthDate extends BirthDate {

    public function setBirthDate($birth_date) {
        //if $birth_date is greater than 150 years throw an exception
        //else pass to parent's setter
        return parent::setBirthDate($birth_date);
    }
}

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

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

বলুন আপনার সাথে একটি কর্মচারী শ্রেণি রয়েছে setHiredএবং setHireDate। কর্মচারীকে ভাড়া হিসাবে নির্ধারণ না করে কাউকে ভাড়ার তারিখ নির্ধারণ করা বৈধ নয়। তবে আপনি এটি প্রয়োগ করার কোনও উপায় নেই। আপনি যদি এই সেটারগুলির একটিতে এটি প্রয়োগ করেন তবে আপনি "সেটিং" এর অর্ডারে চাপ দিচ্ছেন এবং এর জন্য কোনও বিকাশকারীকে জানতে আরও কোড পঠন প্রয়োজন। তারপরে আপনি যখন কোনও পদ্ধতিটি করতে যান তখন $employee->promote($newPosition);যাচাইকরণ হয়েছে কিনা তা ধরে নিতে আপনাকে একটি পতাকা পরীক্ষা করে দেখতে হবে বা ধরে নেওয়া হয়েছে যে এটি করা হয়নি এবং আবার এটি করতে হবে (অপ্রয়োজনীয়)।
প্রগ্রেহামার

পরিবর্তে, মিথস্ক্রিয়া ক্যাপচার। সম্ভবত $employee->updateWorkStatus($hired, $hireDate);বা আরও উন্নত যদি $employee->adminUpdate(\Employee\AdminUpdateDTO $dto);। এখন আপনার প্রয়োজনীয় প্রসঙ্গে আপনি যাচাই করতে পারেন এবং কোনও অতিরিক্ত বৈধতা আদৌ প্রয়োজন কিনা তা সিদ্ধান্ত নিতে পারেন।
প্রগ্রেহামার

আপডেট ওয়ার্ক স্ট্যাটাস মূলত একটি সেটার ফাংশন যা 1 মানের পরিবর্তে 2 সেট করে তবে ধারণাটি একই। এটি করার একটি উপায় তবে আপনি প্রাসঙ্গিক বৈধতা একটি সাধারণ পদ্ধতিতেও রাখতে পারেন যা কেবল তখনই চালিত হয় যখন সমস্ত সম্পত্তি যা একসাথে যাচাইকরণের প্রয়োজন হয় সেট করা হয় অর্থাৎ বৈধতার প্রাসঙ্গিক অংশটি সেটহায়ার্ডডেট এবং সেটহায়ার্ড উভয় দ্বারা কল করা হবে তবে কেবল চলবে যদি উভয়ই আইসেট ভাড়া নেওয়া হয় এবং আইসেট ভাড়া নেওয়া তারিখ সত্য হয়।
ফিজিটি্রি

0

এই পোস্টটি বিশেষত নয় __getএবং __setবরং __callপদ্ধতি কলিং ব্যতীত একই ধারণা। একটি নিয়ম হিসাবে, আমি কোনও ধরণের যাদু পদ্ধতি থেকে দূরে থাকি যা মন্তব্যগুলি এবং পোস্টগুলিতে বর্ণিত কারণে ওভারলোডিংয়ের অনুমতি দেয় , আমি সম্প্রতি একটি তৃতীয় পক্ষের এপিআইতে দৌড়েছি যা আমি ব্যবহার করি যা সার্ভিস এবং একটি সাব-সার্ভিস ব্যবহার করে, উদাহরণস্বরূপ :

http://3rdparty.api.com?service=APIService.doActionOne&apikey=12341234

এর গুরুত্বপূর্ণ অংশটি হ'ল এই এপিআইতে সাব-অ্যাকশন বাদে সবকিছুই একই থাকে doActionOne । ধারণাটি হ'ল বিকাশকারী (আমি এবং এই শ্রেণিটি ব্যবহার করা অন্যরা) সাব-সার্ভিসটিকে নামের মতো কল্পনা করতে পারে:

$myClass->doAction(array('service'=>'doActionOne','args'=>$args));

পরিবর্তে আমি করতে পারতাম:

 $myClass->doActionOne($args);

হার্ডকোড করার জন্য এটি কেবলমাত্র অনেকগুলি সদৃশ হবে (এই উদাহরণটি খুব আলগাভাবে কোডের সাথে সাদৃশ্যপূর্ণ):

public function doActionOne($array)
    {
        $this->args     =   $array;
        $name           =   __FUNCTION__;
        $this->response =   $this->executeCoreCall("APIService.{$name}");
    }

public function doActionTwo($array)
    {
        $this->args     =   $array;
        $name           =   __FUNCTION__;
        $this->response =   $this->executeCoreCall("APIService.{$name}");
    }

public function doActionThree($array)
    {
        $this->args     =   $array;
        $name           =   __FUNCTION__;
        $this->response =   $this->executeCoreCall("APIService.{$name}");
    }

protected function executeCoreCall($service)
    {
        $cURL = new \cURL();
        return $cURL->('http://3rdparty.api.com?service='.$service.'&apikey='.$this->api.'&'.http_build_query($this->args))
                    ->getResponse();
    }

তবে __call()আমি ম্যাজিক পদ্ধতিতে গতিশীল পদ্ধতিতে সমস্ত পরিষেবা অ্যাক্সেস করতে সক্ষম হয়েছি:

public function __call($name, $arguments)
    {
        $this->args     =   $arguments;
        $this->response =   $this->executeCoreCall("APIService.{$name}");   
        return $this;
    }

ডেটা ফেরত দেওয়ার জন্য এই গতিশীল কলিংয়ের সুবিধাটি হ'ল যদি বিক্রেতা অন্য একটি উপ-পরিষেবা যুক্ত করে তবে আমাকে ক্লাসে অন্য কোনও পদ্ধতি যুক্ত করতে বা একটি বর্ধিত শ্রেণি তৈরি করতে হবে না ইত্যাদি this এটি নিশ্চিত কিনা আমি নিশ্চিত নই যে কেউ, কিন্তু আমি আমি একটি উদাহরণ যেখানে দেখাতে হবে মূর্ত __set, __get, __call, ইত্যাদি বিবেচনার জন্য একটি বিকল্প হতে পারে যেহেতু প্রাথমিক কাজ ডেটার দিকেই প্রত্যাবর্তন হবে।


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

কাকতালীয়ভাবে, আমি পোস্টের কয়েক দিন পরে এটি দেখেছিলাম যা আমার দৃশ্যের ঠিক রূপরেখা দেয়। এটি আমি যে এপিআইটি উল্লেখ করছিলাম তা নয় তবে পদ্ধতিগুলির প্রয়োগটি অভিন্ন:

আমি কি এপিআই সঠিকভাবে ব্যবহার করছি?


-2

আপডেট: এই উত্তরটি ব্যবহার করবেন না কারণ এটি শিখার সময় আমি খুঁজে পেয়েছি d কেবল প্লেইন গেটর এবং সেটার ব্যবহার করুন, এটি আরও ভাল।


আমি সাধারণত সেই পরিবর্তনশীল নামটি ফাংশন নাম হিসাবে ব্যবহার করি এবং সেই ফাংশনে alচ্ছিক প্যারামিটার যুক্ত করি তাই যখন optionচ্ছিক পরামিতি কলার দ্বারা পূরণ করা হয়, তারপরে এটি সম্পত্তিতে সেট করে ফিরে আসুন $ এই বস্তুটি (শৃঙ্খলিত) এবং তারপরে যখন optionচ্ছিক পরামিতি দ্বারা নির্দিষ্ট করা হয় না কলার, আমি কেবল কলারকে সম্পত্তি ফিরিয়ে দিই।

আমার উদাহরণ:

class Model
{
     private $propOne;
     private $propTwo;

     public function propOne($propVal = '')
     {
          if ($propVal === '') {
              return $this->propOne;
          } else {
              $this->propOne = $propVal;
              return $this;
          }
     }

     public function propTwo($propVal = '')
     {
          if ($propVal === '') {
              return $this->propTwo;
          } else {
              $this->propTwo = $propVal;
              return $this;
          }
     }
}

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