ひよっこPGのブログ

主に、技術メモや英語たまにギター関連のことも書いているブログです。

プログラマーに対して、面接官になったら尋ねるべき質問実例集を自分なりに回答してみました。

ryoさんが書かれた下の記事を読んで自分なりに回答してみようと思ったのでこの記事を書きました。
プログラマーの力量を見極める質問に回答してみる - 涼の成長記録

  • 「等値」と「等価」の違いを説明してください(この質問はTechRepublicのTony Patton氏に教えてもらったものである)。
  • 「値渡し」と「参照渡し」の違いは何ですか?オブジェクト指向システムや手続き型システムにおいて、これらにはどのような違いが存在するのかを説明してください。
  • ポリモーフィズム」とは何かを説明してください。
  • 「悲観的ロック」と「楽観的ロック」を比較し、違いを明確に述べてください。

 これらの質問のうち、最初の2つに答えられない応募者は、どう考えても「入門者レベル」ということになる。また残り2つの質問は、「中級」開発者であれば答えられるはずである。

引用元 : プログラマーの力量を見極める--面接官になったら尋ねるべき質問実例集 - ZDNet Japan

等値と等価の違い

package test2;

public class Test {
	public static void main(String args[]){
		
		// 本来なら等しくありませんと 出るべきですが
		// Javaの内部で 最適化されて、"hoge" 一つのみがメモリに保存されているみたいです。
		String a = "hoge";
		String b = "hoge";
		if( a == b){
			System.out.println("等しいです。");
		}else{
			System.out.println("等しくありません。");
		}
		
		// 上記の最適化がなされないように途中で文字列結合して同じ内容にしています。
		String c = "hoge";
		String d = "ho";
		d = d + "ge";
		
		// 等値比較
		if( c == d){
			System.out.println("等値比較 : 等しいです。");
		}else{
			System.out.println("等値比較 : 等しくありません。");
		}
		
		// 等価比較
		if( c.equals(d)){
			System.out.println("等価比較 : 等しいです。");
		}else{
			System.out.println("等価比較 : 等しくありません。");
		}
	}
}

実行結果

等しいです。
等値比較 : 等しくありません。
等価比較 : 等しいです。

c == dでは、cとdのメモリ保存場所が同じですか? という意味です。
c と d では文字列の内容は同じですが、メモリの保存場所が違うので 等しくありませんと表示されている感じです。

c.equals(d)では cとdは同じ内容ですか? という意味です。
c : "hoge"
d : "ho" + "ge" = "hoge"
cとdは同じ"hoge"という同じ文字列なので 等しいです。と表示されます。

値渡しと参照渡しの違い

package test2;

public class Test2 {
	public static void main(String args[]){
		
		// 値渡し
		String a = "aaa";
		String b = a;
		b = "bbb";
		System.out.println("aの値は : "+a);
		System.out.println("bの値は : "+b);
		
		// 参照渡し
		User user1 = new User();
		user1.setName("Buzz");
		User user2 = user1;
		user2.setName("Woody");
		System.out.println("user1のnameは : "+user1.getName());
		System.out.println("user2のnameは : "+user2.getName());
	}
}

class User{
	private String name;
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
}

実行結果

aの値は : aaa
bの値は : bbb
user1のnameは : Woody
user2のnameは : Woody
String b = a

上記は、値渡しになります。
aの内容ごとコピーしてbに代入するという意味です。
なのでa と bの内容は独立しています。

User user2 = user1;
user2.setName("Woody");

上記は、参照渡しになります。
user1のメモリ保存場所を user2に代入するという意味です。
なので、user2に変更を加えると user1に影響が出ます。

ポリモーフィズム

package test2;

public class Test3 {
	public static void main(String args[]){
		Red  red  = new Red("赤");
		Blue blue = new Blue("青");
		
		viewColor(red);
		viewColor(blue);
	}
	
	// 色を表示するメソッド
	public static void viewColor(Color color){
       System.out.println("色の名前は : "+color.getName() );
	}
}

// カラーインタフェース
interface Color{
 // 色の名前を返す
 String getName();
}


// 赤クラス
class Red implements Color{
    private String name;

    public Red(String name){
        this.name = name;
    }
    public String getName() {
        return name;
    }
}

// 青クラス
class Blue implements Color{
    private String name;

    public Blue(String name){
        this.name = name;
    }
    public String getName() {
        return name;
    }
}

実行結果

色の名前は : 赤
色の名前は : 青

viewColorメソッドは、インタフェース Colorとして受け取って インターフェースで記述している getNameメソッドを実行しています。
同じメソッドを実行しても、違う結果を返す。
あまり上手く説明できないんですが、インタフェースは上記のようなイメージで使っています。
同じインターフェースを実装していればその方として扱うことが出来る。
インタフェースで定義されていることであれば、インターフェース型のままで実行できる。

「悲観的ロック」と「楽観的ロック」

言葉自体初めて聞いたので、調べないと分からないですね。
機会があった時に調べます。





以上自分なりの回答です。
間違いや補足などのコメントいただければとても喜びます!