質問

この質問に答えはこちら

ご容赦下さい長さのだが、ここでは二つのプログラムは、全く同じものとなgetter,setterか、コンストラクタ.

重ねてきた基本的なC++クラスの前を覚のいずれかで、でんなに、すでに説明してもらうようにlamen条件ろくてはならないもので---のようでしょうかなりスペースwastersの場として開かれていてコードを長く見えるように教師というものが重要だということになります(これまでのとします。

感謝。現在こちらのコード:Mileage.java:

package gasMileage;

import java.util.Scanner; //program uses class Scanner

public class Mileage 
{
    public int restart;
    public double miles, gallons, totalMiles, totalGallons, milesPerGallon;
    public Mileage(int newRestart, double newMiles, double newGallons, 
                   double newTotalMiles, double newTotalGallons, double newMilesPerGallon)
    {
        setRestart(newRestart);
        setMiles(newMiles);
        setGallons(newGallons);
        setTotalMiles(newTotalMiles);
        setTotalGallons(newTotalGallons);
        setMilesPerGallon(newMilesPerGallon);
    }
    public void setRestart(int newRestart)
    {
        restart = newRestart;
    }
    public int getRestart()
    {
        return restart;
    }
    public void setMiles(double newMiles)
    {
        miles = newMiles;
    }
    public double getMiles()
    {
        return miles;
    }
    public void setGallons(double newGallons)
    {
        gallons = newGallons;
    }
    public double getGallons()
    {
        return gallons;
    }
    public void setTotalMiles(double newTotalMiles)
    {
        totalMiles = newTotalMiles;
    }
    public double getTotalMiles()
    {
        return totalMiles;
    }
    public void setTotalGallons(double newTotalGallons)
    {
        totalGallons = newTotalGallons;
    }
    public double getTotalGallons()
    {
        return totalGallons;
    }
    public void setMilesPerGallon(double newMilesPerGallon)
    {
        milesPerGallon = newMilesPerGallon;
    }
    public double getMilesPerGallon()
    {
        return milesPerGallon;
    }
    public void calculateMileage()
    {
        Scanner input = new Scanner(System.in);
        while(restart == 1)
        {
            System.out.print("Please input number of miles you drove: ");
            miles = input.nextDouble();
            totalMiles = totalMiles + miles;
            System.out.print("Please input number of gallons you used: ");
            gallons = input.nextDouble();
            totalGallons = totalGallons + gallons;
            milesPerGallon = miles / gallons;
            System.out.printf("Your mileage is %.2f MPG.\n", milesPerGallon);
            System.out.print("Would you like to try again? 1 for yes, 2 for no: ");
            restart = input.nextInt();
        }
        milesPerGallon = totalMiles / totalGallons;
        System.out.printf("Your total mileage for these trips is: %.2f.\nYour total gas consumed on these trips was: %.2f.\n", totalMiles, totalGallons);
        System.out.printf("Your total mileage for these trips is: %.2f MPG", milesPerGallon);
    }
}

Mileagetest.java:

package gasMileage;

public class Mileagetest 
{
    public static void main(String[] args) 
    {
        Mileage myMileage = new Mileage(1,0,0,0,0,0);
        myMileage.calculateMileage();
    }
}

このなgetterおよびsetterか:

Testmileage.java:

package gasMileage;

import java.util.Scanner;

public class Testmileage 
{
    int restart = 1;
    double miles = 0, milesTotal = 0, gas = 0, gasTotal = 0, mpg = 0;
    Scanner input = new Scanner(System.in);
    public void testCalculate()
    {
        while(restart == 1)
        {
            System.out.print("Please input miles: ");
            miles = input.nextDouble();
            milesTotal = milesTotal + miles;
            System.out.print("Please input gas: ");
            gas = input.nextDouble();
            gasTotal = gasTotal + gas;
            mpg = miles/gas;
            System.out.printf("MPG: %.2f", mpg);
            System.out.print("\nContinue? 1 = yes, 2 = no: ");
            restart = input.nextInt();
        }
            mpg = milesTotal / gasTotal;
            System.out.printf("Total Miles: %.2f\nTotal Gallons: %.2f\nTotal MPG: %.2f\n", milesTotal, gasTotal, mpg);
    }
}

Testmileagetest.java:

package gasMileage;

public class Testmileagetest 
{

    /**
     * @param args
     */
    public static void main(String[] args) 
    {
        Testmileage test = new Testmileage();
        test.testCalculate();
    }

}

感謝!

役に立ちましたか?

解決

ゲッターとセッターの点は、の言語に関係なくの、基礎となる変数を隠蔽することです。これは、値を設定しようとしたときに検証ロジックを追加することができます - たとえば、あなたが誕生日のためのフィールドを持っていた場合、あなただけの過去のある時点にそのフィールドを設定できるようにしたい場合があります。フィールドが公にアクセス可能とmodifyableである場合、これは強制することはできません - あなたはゲッターとセッターを必要とする

あなたはまだ検証が必要ない場合でも、あなたが将来的にそれが必要になる場合があります。ゲッターとセッターを書くことになりましたインタフェースの一貫性が保たれることを意味するので、あなたはそれを変更する場合、既存のコードが中断されません。

他のヒント

その他の回答は良いアイデアの理由をsetterか、セッターが教えていてやりがいも感じるのはやや完全さを説いています。

みましょう、例えば、ファイルを無視しての存在を File クラスJava).この File クラス分けを格納するタイプのファイル(.pdf,.exe,.txtなど)...ま無視します。

当初決まりました店舗として String 無setterか、セッター:

public class File {
   // ...
   public String type;
   // ...
}

この問題を使用しないsetterか、セッター.

管理方法の設定:

任意のクライアントのクラスが自由に活動していないものとします。

public void doSomething(File file) {
   // ...
   file.type = "this definitely isn't a normal file type";
   // ...
}

決まりましたらその後ませんがどうなっているか示されていないのに---がほとんどなされていなかった直接のアクセス分野をタンをクリックして下さいませんの防止します。

なに簡単に変更の内部表現は:

後のものが決まりましたら保存するファイルタイプとしてのインスタンスのインタフェースと呼ばれ FileType, を可能にし、准一部の挙動が異なるファイルの種類です。しかし、多くのクライアントのクラスは既に取得、設定ファイルの種類として Strings.ない問題があ---ん休憩を多くのコードでもコードを他のプロジェクトがまだ自分の場合は、図書室だけの分野から StringFileType.

どのようsetterか、セッターの解決に向けた

このことだったのではなく、タイプ分野 private

public String getType() {
   return this.type;
}

public void setType(String type) {
   this.type = type;
}

制御設定の物件:

現したいときに実施する必要があった文字列は有効なファイルの種類の防止その他の文字列だけなのに書き:

public void setType(String type) {
   if(!isValidType(type)) {
       throw new IllegalArgumentException("Invalid file type: " + type);
   }
   this.type = type;
}

private boolean isValidType(String type) {
   // logic here
}

簡単に変更の内部表現は:

を変更する String 表現型は比較的容易です。たとえば enum ValidFileType を実装する FileType を含むの有効なタイプのファイルです。

きの変更が容易に内部表現をファイルタイプのクラスのようになります:

public class File {
   // ...
   private FileType type;
   // ...
   public String getType() {
      return type.toString();
   }

   public void setType(String type) {
      FileType newType = ValidFileType.valueOf(type);

      if(newType == null) {
         throw new IllegalArgumentException("Invalid file type: " + type);
      }

      this.type = newType;
   }
}

以来、お客様のクラスを呼びかけておりますが、これま getType()setType() とにかく、何も変化からの視点です。の内部クラスの変更はいたインターフェースのその他の授業を利用しています。

封止

アクセス用メソッド("getterおよびsetterか"に非表示についての詳細はどのようにデータをオブジェクトが格納されています。実際には、この栄光を保存-取得するデータ以外のオブジェクト指向ファッション。Accessorsない効果的に閉じない実践的違いは以下の二つのコード:

Person bob = new Person();
Colour hair = bob.getHairColour();
hair.setRed( 255 );

この:

Person bob = new Person();
Colour hair = bob.hairColour;
hair.red = 255;

両コードスニペットを露出させたという人は強く結合す。この締結を明らかにそのコードをベースにより脆化ソフトウェアです。ることが困難になり変化をどのように人の髪の毛が格納されています。

代わり:

Person bob = new Person();
bob.setHairColour( Colour.RED );

り組んでおり、その一環として企業の前提として名前が挙がっていないお願いします。" つまり、オブジェべきことを指示し(その他のオブジェクト)を特定の課題です。この点に着目したオブジェクト指向プログラミング非常に少ない人と思います。

との間の差は二つのシナリオをここに

  • 最初の状況、Bobがどの色の髪ることになりそうです。大のためのヘアスタイリストと好redheadsいてくることBobの方despisesれるようになります。
  • の状況、ボブは完全に制御で何色の髪の毛をとめないその他のオブジェクトのシステムが変更させる色ずBobます。

別の言い方をこの問題を回避するためにはコピーを返しのボブの髪の毛の色と新しいインスタンスはないとの結合をBobそれinelegant溶液であるということは行動する別のクラスを希望、人毛髪ではなく、人そのものです。低減する機能を再利用コード、複製します。

隠蔽データの種類

Javaでは、二つのメソッドシグニチャーだけが異による戻り値の型であることが発表されない隠しを配下のデータタイプが使用するオブジェクトです。まほらばんはこちら

public class Person {
  private long hColour = 1024;

  public Colour getHairColour() {
    return new Colour( hColour & 255, hColour << 8 & 255, hColour << 16 & 255 );
  }
}

通常、個々の変数のデータタイプの露出によるバーベイタムの使用に対応するアクセス用メソッド、リファクタリングに変更す:

public class Person {
  private long hColour = 1024;

  public long getHairColour() {
    return hColour;
  }

  /** Cannot exist in Java: compile error. */
  public Colour getHairColour() {
    return new Colour( hColour & 255, hColour << 8 & 255, hColour<< 16 & 255 );
  }
}

ないレベルの抽象化では、薄いヴェールで何もしないためゆったりカップリングです。

考えてい

詳細は、この考えを読む 考えてい.

ファイルの例

考え、以下のコードでは、わずかに修正しColinDの回答:

public class File {
   private String type = "";

   public String getType() {
      return this.type;
   }

   public void setType( String type ) {
      if( type = null ) {
        type = "";
      }

      this.type = type;
   }

   public boolean isValidType( String type ) {
      return getType().equalsIgnoreCase( type );
   }
}

の方法 getType() このインスタンスで冗長ない(実践)"で繋がる重複コードなど

public void arbitraryMethod( File file ) {
  if( file.getType() == "JPEG" ) {
    // Code.
  }
}

public void anotherArbitraryMethod( File file ) {
  if( file.getType() == "WP" ) {
    // Code.
  }
}

問題:

  • データ型になります。type 属性は容易に変更からStringを整数値(または別のクラス)
  • 暗黙のプロトコルです。 でには時間がかかる旨のタイプから具体的PNG, JPEG, TIFF, EPS の一般IMAGE, DOCUMENT, SPREADSHEET).
  • 紹介させてしまいます。 を変更する暗黙のプロトコルメッセージは生成されませんコンパイラエラーを引き起こす可能性がございます。

問題を回避するために完全に防止その他のクラスから データ:

public void arbitraryMethod( File file ) {
  if( file.isValidType( "JPEG" ) ) {
    // Code.
  }
}

この変更 get アクセス用メソッドの方法 private:

public class File {
   public final static String TYPE_IMAGE = "IMAGE";

   private String type = "";

   private String getType() {
      return this.type;
   }

   public void setType( String type ) {
      if( type == null ) {
        type = "";
      }
      else if(
        type.equalsIgnoreCase( "JPEG" ) ||
        type.equalsIgnoreCase( "JPG" ) ||
        type.equalsIgnoreCase( "PNG" ) ) {
        type = File.TYPE_IMAGE;
      }

      this.type = type;
   }

   public boolean isValidType( String type ) {
      // Coerce the given type to a generic type.
      //
      File f = new File( this );
      f.setType( type );

      // Check if the generic type is valid.
      //
      return isValidGenericType( f.getType() );
   }
}

他にはないコードのシステム休憩時の File クラス転移の暗黙のプロトコルから特定の種類(例えば、JPEG)への汎用タイプ(例えば、画像)となっています。すべてのコードシステムのものを使用しなければな isValidType 方法は、いませんのタイプ、呼び出し元のオブジェクトが File クラスの有効性を実証タイプです。

アイデアは、あなたのクライアントクラスを取得/設定関数を呼び出す場合、あなたは彼らが後で行い、発信者が絶縁されているものを変更することができるということです。あなたがパブリック変数を持っている、と私はそれを直接アクセスする場合は、後でそれがアクセスまたは設定されている場合の動作を追加するための方法はありません。

でも、あなたの簡単な例では、あなたはそれをより多くの利点を取ることができる。

の代わりに使用したのます:

milesPerGallon = miles / gallons;

calculateMileageに()

あなたは彼らが呼ばれたときmilesPerGallonを更新する)setMiles()とsetGallonsを(変更することができます。その後、それは読み取り専用のプロパティだことを示すためにsetMilesPerGallon()を削除します。

ポイントは、これは実装固有であるため、クラスは、そのフィールドへの直接アクセスを許可してはならないということです。あなたは別のデータストレージを使用するためには、後にクラスを変更したいのですが、その「ユーザー」のために同じクラスを維持するか、どちらかのフィールドを含めることはできませんインターフェースを作成したい場合があります。

テーマに関するウィキペディアの記事のを見てください。

彼らはあなたのクラスのパブリックインターフェイス、およびカプセル化のいくつかの手段を提供します。あなたはgetterとsetterなしで公開データにアクセスする方法を考えてみます。

Mileage m = new Mileage();
m.miles = 5.0;
m.gallons = 10.0;
...
あなたがあなたのクラスにいくつかの検証を追加することにした場合、

さて、あなたはフィールドに直接アクセスされたことをどこでもあなたのコードを変更する必要があります。あなただけの開始からゲッターとセッターを使用している場合(の彼らだけが必要とされる場所の)あなたはその努力を避け、そして唯一の場所にコードを変更することができます。

ゲッターとセッターを使用すると、あなたの後から実装を変更するための柔軟性を提供します。あなたはそれが必要だと思うかもしれませんが、時にはあなたが行います。たとえば、遅延ロードに使用するには高価であるオブジェクトをプロキシパターンを使用する場合があります:

class ExpensiveObject {
    private int foo;

    public ExpensiveObject() {
       // Does something that takes a long time.
    }

    public int getFoo() { return foo; }
    public void setFoo(int i) { foo = i; }
}

class ExpensiveObjectProxy extends ExpensiveObject {
    private ExpensiveObject realObject;

    public ExpensiveObjectProxy() { ; }

    protected void Load() {
       if ( realObject == null ) realObject = new ExpensiveObject();
    }

    public int getFoo() { Load(); return realObject.getFoo(); }
    public void setFoo(int i) { Load(); realObject.setFoo(i); }
}

class Main {
    public static void main( string[] args ) {
         // This takes no time, since ExpensiveOjbect is not constructed yet.
         ExpensiveObject myObj = new ExpensiveObjectProxy();

         // ExpensiveObject is actually constructed here, when you first use it.
         int i = myObj.getFoo();
    }
}
あなたはORMを通じてデータベースにマッピングされたオブジェクトを持っている場合、

これは、多くの場合、再生するために出番があります。あなたが唯一、それが実際に使用されたときに/場合は残りの部分をロードするためにデータベースに戻って、その後、あなたが必要なものをロードします。

一般セッターとゲッターでは、

(本当に、これは絶対に必要である)すべての変数がprivateである必要がありますということを回避するために早期のGUIビルダー(ボーランド)によって悪いハックました

一部の人々は、抽象それらを呼び出すが、そうではありません。定型セッター/ゲッターは、パブリックメンバーよりも良いではありません。彼らはまだあなたの変数がint型である場合、あなたはまだ文字列に変数を変更するにはセッターを呼び出し、すべてのものとゲッターを変更する必要があります(クラスは、クラスの変更を制御し、それでも制限することはできませんの回で、変数へのフルアクセスを許可します)

GetterおよびSetterは、クラスの外からのクラスのデータにアクセスする奨励します。クラスのメンバにアクセスするコードは、おそらく(あなたのデザインの状態として)、そのクラス内に存在しなければならないので、セッターやゲッターを必要はありません。彼らは、不要であるべきである。

また、すべてのクラスにセッターを強制することは、あなたが実際にクラスが変更可能にする本当に良い理由を持つべきであるのに対し、あなたのクラスは、単純に不変ではないことを意味し、恐ろしいです。

、彼らは親切持続性エンジンとGUIビルダーのような横断的関心事彼らが得ると値を設定し、クラスがそれを得たか、変更されたものを監視し、変更または検証することができのための便利です言った。

直接反射を介して変数にアクセスするBUTセッターを呼び出すかが存在する場合にゲッタリングすることで横断的変数のアクセスを必要とするシステムのためのより良いパターン - セッターを作り、プライベート可能であればゲッタリング

これはあなたのクラスはセットを変更することができ、それがする必要があるときに取得し、(時には本当に便利です)ゲッター必要な場合を可能にする、正しく動作するために、非OO横断的なコードを可能にする。

アクセサメソッドのポイントは、IE。ゲッターとセッターは、カプセル化AKAの情報隠蔽を提供することです。これは、オブジェクト指向プログラミングの基本的な原則の一つです。

する

情報表示/非カプセル化する

一言で答えがのインターフェースのです。

インターフェースはメソッドではなく、フィールドを可能にするので、設立条約は、この目的のためのgetXとSETXメソッドを持つことです。

(およびインタフェースは、Javaで実装から機能を分離するための方法である)

おの例は極端に不条理.はい、すべてのsetterか、膨張セッターのコードと付加価値る場合があります。もりの基本の封止その他の事由による事故があったがこれらを組み合わせたシステムで多くの機体は、小型の自己含まれる。

特性、良識あるのsetterか、セッター:

  • クラスで使用される他の多くの授業をしない●実施内容を容易にクライアント)
  • Setterか、セッターのみのためにどの分野の彼らは実際に必要として、数として、大部分の分野では、民間だけに使用される範囲内にクラス
  • 非常に少数の一般セッター:変更可能な分野であったが、それができなくなっ跡プログラムの状態により読み取り専用分野
  • Setterか、セッターが実際に 以外のものにアクセスするナイズされちゃなどセッターと例外をスロー無効な値を更新、"更新"タイムスタンプ、ゲッターを計算する値のフライを信頼するのではなく、基本となるフィールド

早送り数ヶ月。たぶんあなたの先生は、走行距離のクラスのリモートバージョンを実装するように求められます。多分、多分、Webサービス、何か他のもののように。

ゲッター/セッターがなければ、あなたはA acccessesどこでも、すべてのコードを変更する必要があると思います 走行距離は、ゲッター/セッターであなたはかなり(少なくとも、完璧な世界では)ちょうど走行距離タイプの作成を変更する必要があります。

GetterおよびSetterを使用すると、オブジェクト内のデータにアクセスし、変異のための便利なショートカットを構築することを可能にします。一般に、これは、取得した値を設定するために使用されているオブジェクトに二つの機能を有することに代わるものとして見ることができるようなので

{
    getValue: function(){
        return this._value;
    },
    setValue: function(val){
        this._value = val;
    }
}

この方法ではJavaScriptを書くことへの明白な利点は、あなたがそれをあなたが直接アクセスするためのユーザーを望んでいない無名の値を使用することができるということです。

:(新たに建設されたフィールドの値を格納するためにクロージャを使用して)次のようなものを探して、最終的な結果
function Field(val){
    var value = val;

    this.getValue = function(){
        return value;
    };

    this.setValue = function(val){
        value = val;
    };
}

setterメソッドとgetterメソッドを追加します マネージドBeanの状態にアクセスできるようにするには、その状態のsetterとgetterメソッドを追加する必要があります。 createSalutation方法はbean'sgreetメソッドを呼び出し、そしてgetSalutation方法は、結果を取得します。 setterメソッドとgetterメソッドが追加されたら、Beanは完了です。最終的なコードは次のようになります。 パッケージ挨拶;

import javax.inject.Inject;
import javax.enterprise.context.RequestScoped;
import javax.inject.Named;

@Named
@RequestScoped
public class Printer {

    @Inject @Informal Greeting greeting;

    private String name;
    private String salutation;

    public void createSalutation() {
        this.salutation = greeting.greet(name);
    }

    public String getSalutation() {
        return salutation;
    }
    public String setName(String name) {
       this.name = name;
    }

    public String getName() {
       return name;
    }
}

封止コード再利用-能力 の美しさのオブジェクト指向プログラミングの場合を取り扱っております一部の機密データにコードをすることを宣言いたします個人データの分野にまた封止当社のデータだけでなく、さまざまな取り組みがアクセストールしてください現在一人のアクセスデータを分野かしてほしいと思いますgetterおよびsetterかつ制御されたアクセス機構を扱いいたします。以下の例では、今後はクリエイティビティを理解する利点は、重要性のセッターとsetterか.

  • ってクラスを作っていますの使用日数に変更します。
  • 私のクラスでの値を設定します日以365.
  • 一人からは継承しました。(コード再利用).
  • 今の時代に入り値の日以365日、そのすべての機能は私のクラスに失敗します。
  • そのためばいいのかを宣言しての変数として個人データの分野です。
  • 今ましたし、宣言された日のデータフィールドとして貸しなの値を設定します日数を365日としてこの行セッター機能上の制限入力します。
ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top