OOP Lab 7(25 pts)

Due date : May 3, 23:59


Submit your assignment using the following file format:

   LabNumber_StudentName_Student_ID.zip

   Example: Lab7_Hongkildong_201620505.zip

 

This  zip file will contain two types of files, namely:

1)      report file with file format  Report_Lab number (eg. report_7) to answer theory questions and to write the screen shot of your program.

2)      Source code file that contains codes of classes to answer programming questions.

Contents


1)     In java, Object class is the root class in class hierarchy. The Object class defines the following common methods shared by any subclass of the Object class.

    a)     public String  toString()

    b)     public native int hashCode()

    c)     public boolean equals(Object o)

    d)     public final Class getClass()

 

2)      Use of “Class” class and java Reflection API.  


Problem 1(4pt): Write and run the following code.

a) When you run the code, an error is generated. What is the cause of the error? (2pt)

Answer :

There is no package in need to call "Method" class.

Method[] getDeclaredMethods(): Returns all method information declared in that class.
We can use the "Method" class to get information about the method. However, there is no constructor in the "Method" class, so we must use the "GetMethods()" method in the "Class" class or the "getDeclaredMethod()" method to obtain information in the "Method" class. 
Java APIs have a package called "reflection," which allows you to use the classes in which you can read class and method information that is loaded into the JVM.

 

Method[] getDeclaredMethods(): 해당 클래스에서 선언된 모든 메소드 정보를 리턴한다.

"Method" 클래스를 이용하여 메소드에 대한 정보를 얻을 수 있습니다. 하지만, "Method" 클래스에는 생성자가 없어서, "Method" 클래스의 정보를 얻기 위해서 "Class" 클래스의 "getMethods()" 메소드를 사용하거나 "getDeclaredMethod()" 메소드를 써야합니다. 

자바 API에는 "reflection"이라는 패키지가 있는데, 이 패키지에 있는 클래스들을 써서 JVM에 로딩되어 있는 있는 클래스와 메소드 정보를 읽어 올 수 있습니다. 

 

b) Re-write the program correctly and show the screenshot of the program (3pt)

 


Problem 2(3pt): toString () method of “Object” class  

// Student.java
class Student
{
    String name;
    int ID; 
    public Student(String name, int ID)
    {
        this.name=name;
        this.ID=ID;
    }
    public String toString()
    {
        return “Student name:” + name + ”and ID:” + ID;         
    }       
    public static void main (String []args )
    {
        Student S1 = new Student(“kim”, 101);
        Student S2 = new Student(“Homin”, 102);
        System.out.println(S1);                 /* 1  */          
        System.out.println(S1.toString());    /* 2 */        
        System.out.println(S2);                 /* 3 */                
   }       
}

a) run the following code and take the screenshot (1pt) 

 

b) From 2(a), comment Line 10-13 and run the program. Show the screen shoot. Why the screen shot is different from 2(a)? Explain your answer (2pt).  

Answer : Since the "Object" class is inherited by the "Student" class, but did not override. By commenting a 10-13 line, the "toString()" method of the "Object" class is performed as it is. So the screen shot is different from 2(a).

 

"Object"클래스를 "Student" 클래스가 상속하지만 10-13 주석을 닮으로써, override 하진 않았으므로, "Object" 클래스의 "toString()" method가 그대로 수행되기 때문에 screen shot is different from 2(a).

 

 

"Object"클래스의 toString() method "Student" 클래스에 overiding했다.

"main" method에서 "S1"인스턴스를 System.out.println의 인자로 전달하니까 toString() method를 명시적으로 호출하지 않았음에도 동일한 효과가 나고 있다.


Problem 3(6pt): Answer all the questions based on the following code.       

import java.util.*;
public class Test {
	public static void main(String args[])
	{
		String s = new String("kim");
		System.out.println(s);
		Integer i = new Integer (10);
		System.out.println(i);
		Test t = new Test();
		System.out.println(t);
		
	}
}

a) Is java.lang.String class override toString() method of “Object” class? Explain your reason. Hint: refer line 6 (2pt)

Answer : No. Because the “String” class extends “Object” class, but not overrides. The "String" class just uses “toString()” method of the "Object" class. And the "String" type instance "s" is using "System.out.println", which has the same effect even though the "toString()" method has not been explicitly called like “s.toString()”.

 

a) java.lang.String 클래스는 Object 클래스의 toString() 메써드를 오버라이딩 하고 있는가?  아니오!

String 클래스가 Object 클래스의 toString() 메쏘드를 상속받음으로써 String 타입의 값을 반환할수 있다.

상속 ≠ 오버라이딩

b) Is java.lang.Integer class override toString() method of “Object” class?  Explain your reason. Hint: refer line 8(2pt)

Answer : No. Because the “Integer” class extends “Object” class, but not overrides. The "Integer" class just uses “toString()” method of the "Object" class. And the "Integer" type instance "i" is using "System.out.println", which has the same effect even though the "toString()" method has not been explicitly called like “i.toString()”.

 

c) Is Test class override toString() method of “Object” class? Explain your reason. Hint: refer line 10(2pt)

Answer :

No.

The “Object” class is a superclass of all Java classes.

The “Object” class has no field to be inherited by all other classes and it has "toString()" methods that are inherited or overridden by other classes.

The “Object” class defines the "toString()" to print the class name.

"toString()" method of "Object" class was inherited in "Test" class.
The "Test" class just uses the “toString()” method of "Object" class, and the "Test" type instance "t" is using "System.out.println", which has the same effect even though the "toString()" method has not been explicitly called.

 


Program 4(6pt): Answer all the question based on the following code. 

class Test 
{
	int i;
	
	public Test(int i)
	{
		this.i = i;
	}
	public int hashCode()
	{
		return i;
	}
	public String toString()
	{
		return i + " ";
	}
	public static void main (String []args)
	{
		Test t1 = new Test(10);
		Test t2 = new Test (100);
		System.out.println(t1);
		System.out.println(t2);
	}
}

a) comment Line 9-16 and see the output. Why you get this output?(2pt)

Answer :

The toString() method returns information about that instance as a string. 
The string returned at this time is '@' as the delimiter along with the class name, followed by a hexadecimal hash code. 
The hexadecimal hash code value is the value that points to the address of the instance, which is returned differently for each instance. 
In Java, the toString() method is essentially overridden by overriding itself for each API class. 
Thus, commenting line 9-16, the toString() method will result in output as "Class name" @ "hash code".

 

toString() 메소드는 해당 인스턴스에 대한 정보를 문자열로 반환한다.

이때 반환되는 문자열은 클래스 이름과 함께 구분자로 '@'가 사용되며, 그 뒤로 16진수 해시 코드(hash code)가 추가된다. 16진수 해시 코드 값은 인스턴스의 주소를 가리키는 값으로, 인스턴스마다 모두 다르게 반환된다. 자바에서 toString() 메소드는 기본적으로 각 API 클래스마다 자체적으로 오버라이딩을 통해 재정의되어 있다. 따라서 toString() method를 주석처리 하면 "Class name" @ "hash code"로 출력된다. 

b) comment only Line 9-12 and see the output. Why you get this output?(2pt)

Answer :

The "hashcode()" method is commented.

And then 10 is inserted in the "Test" type instance "t1", and 100 is inserted in the "Test" type instance "t2".

Thus, commenting line 9-12, outputs as 10 and 100.

 

hashcode() method를 주석처리 해주고 "Test" 타입의 인스턴스 "t1"에 10을 넣어주고, "Test" 타입의 인스턴스 "t2"에 100을 넣어줬으므로 10 과 100이 출력된다.

c) comment only line 13-16 and see the result. Why you get this output?(2pt)

Answer :

hashCode() : Returns the hash code value of the object.

The "hashCode()" method of the "Object" class was overridden to output the entered parameter value, but the "toString()" method of the "Object" class was not overridden.
Thus, commenting line 13-16, outputs as "Class name" @ "overridden hash code".
At this time, the "overridden hash code" value is output in hexadecimal of the parameter value received.

 

"Object" 클래스의 "hashCode" method를 입력 받은 매개변수 값으로 출력하게끔 override 하였고, "Object" 클래스의 "toString()" method를 override 하지 않았다.

 "Class name" @ "overrided hash code"로 출력된다.

이때 "overrided hash code" 값은 입력받은 매개변수 값의 16진수로 출력된다.


Problem 5 (5pt)

a) Run the following Code and take screen shoot (1pt).

b) In the above code, comment Line 10-32 and comment lines 42-43.
What is the output at line 39, 40 and 41? Why you get this output (2pt).

Answer 

The function of “equals()” method is comparing the instance with the reference variable being passed to the parameter and returns the result. If the reference variable compares the value which points to the two different objects, It will return false.

In “Student” class “equals()” method is overriden from "Object" class.

But by commenting line 10-32, “Student” class is only inherited and not overridden from “Object” class.

S1 and S2, S3 give false because the reference variable points to different addresses. 
However, since S4 copies S1, the two reference variables point to the same address, resulting in true.

 

equals() 주석처리하고 맨마지막 kim, null 주석 처리해라.

39, 40, 41의 결과는? 왜 이런 결과가 나왔는가?

 

boolean equals(Object obj) : Returns whether the object and the object received are the same.

equals() 메서드는 해당 인스턴스를 매개변수로 전달받는 참조 변수와 비교하여, 그 결과를 반환한다.

이때 참조 변수가 가리키는 값을 비교하므로, 서로 다른 두 객체는 언제나 false를 반환하게 된다.

S1과 S2, S3는 참조 변수가 다른 주소를 가르키므로 false가 나온다 

다만, S4는 S1를 복사하므로 두 참조 변수가 같은 주소를 가르키게 되어 true가 나온다.

 

다음 예제는 equals() 메소드를 이용하여 두 인스턴스를 서로 비교하는 예제이다. 다만, c2를 c1에 복사하면 두 참조 변수가 같은 주소를 가리키게 되어 true가 나온다. 자바에서 equals() 메소드는 기본적으로 각 API 클래스마다 자체적으로 오버라이딩을 통해 재정의되어 있다.

 

주소값이 아닌 값을 비교하고 싶다면 equals() method를 override 해서 값을 비교하도록 변경하면 된다.

c) In the above code, comment only Line 10-32. Is there error at line 42 and Line 43?  Why? (2pt).

Answer : No

In 42 line, “S1” is compared with the literal(=immidiate value) of the string, It means, the reference variable of “S1” is compared with the other address. So the false comes out.
In 43 line, “S1” is compared with the null value. It means the reference variable of “S1” is compared with other address. So the false comes out.
If we want to compare values other than address values, we should override the equals() method.

 

10-32를 주석처리 해라. 42-43 line에 에러가 있는가?

 

42 line은 문자열의 리터럴 주소와 비교하므로 S1의 참조 변수와 다른 주소를 비교한다. 그래서 false가 나온다.

43 line은 null값과 비교하므로 S1의 참조 변수와 다른 주소를 비교한다. 그래서 false가 나온다.

주소값이 아닌 값을 비교하고 싶다면 equals() method를 override 해서 값을 비교하도록 변경하면 된다.


Reflection은 자바언어의 특징이다. 리플렉션은 자가프로그램이 자기 자신을 조사하거나 "introspect"하는것을 실행하거나,프로그램의 내부 프로퍼티의 조작을 허락한다. 예를 들면, 자바클래스에서 멤버변수나의 이름을 취득하거나, 이름들을 디스플레이 하는것이 가능하다. 스스로의 자바클래스를 조작하거나, 조사하는 능력이 많아 보이지는 않지만, 간단히 다른 프로그래밍언어에는 이러한 특징이없다 

자바빈에 있어서 리플렉션의 구체적인 쓰임중 하나는 빌더 툴을 통해서 비쥬얼적으로 소프트웨어 컴퍼넌트를 조작할수 있따는것이다. 툴들은 리플렉션을 통해서 자바컴퍼넌트(클래스)의 프로퍼티를 알아내고, 동적으로 로딩한다.

이것은 java.util.Stack 클래스에 대한 메소드 이름을 나열하고, 인수들과, 반환값을 나열한것이다. 이 프로그램은 class.forName를 이용하여 특정 클래스를 로딩하고, getDeclaredMethods () 메소드를 통하여, 클래스에 정의되어있는 메소드리스트를 얻어낸다. java.lang.reflect.Method 는 하나의 메소드를 표현한다. 

Setting Up to Use Reflection

Method와 같은 리플렉션 클래스는 in java.lang.reflect 팩키지에서 찾아볼수 있다. 이 클래스를 사용하기위해서는 다음과 같은 과정이 필요하다. 첫번째 과정으로는 조작하고자 하는 클래스의 java.lang.Class 형의 오브젝트를 취득한다. java.lang.Class 은 자바프로그램이 실행될때, 클래스와 인터페이스를 대표한다.



출처: https://otwall.tistory.com/entry/JAVA-리플렉션 [맘먹은대로~]

'📌 java > Object-oriented Programming' 카테고리의 다른 글

java - UML  (0) 2020.05.07
Homework_8  (0) 2020.05.07
java - 업캐스팅 다운캐스팅  (0) 2020.04.26
java - 상속의 참조 관계  (0) 2020.04.26
Homework_W6  (0) 2020.04.23
복사했습니다!