1.
class Ref {
int a;
Ref(int x) {
a=x;
}
int sum (Ref obj) {
int k;
k = obj.a -a;
a = 10; obj.a =20;
return k;
}
}
class passRef {
public static void main(String[] args) {
Ref obj1 = new Ref(3);
Ref obj2 = new Ref(4);
int k1 = obj2.sum(obj1);
System.out.print("k1=" +k1);
System.out.print("obj1.a=" + obj1.a);
System.out.print("obj2.a=" + obj2.a);
}
}
답 : k1 = -1, obj1.a = 20, obj2.a =10
풀이 :
Ref 클래스의 인스턴스 obj1을 생성하면서 생성자를 이용해 a에 3값을 대입
Ref 클래스의 인스턴스 obj2를 생성하면서 생성자를 이용해 a에 4값을 대입
obj1의 멤버 a에는 3, obj2의 멤버 a에는 4값이 대입
obj2.sum(obj1);을 호출하고 , sum 함수에는
- k 지역변수를 선언하고, k에 인자로 받은 obj의 a 값, 즉 obj1이 가지고 있는 3값에서 obj2가 가지고 있는 4값을 빼주게 되어 -1을 k 변수에 대입
- a=10; 지금 메서드를 호출한 인스턴스 obj2의 a값을 10으로
- obj.a = 20; 인자로받은 obj1의 a 값을 20으로 변경
2.
class Subject1 {
protected int a = 1000;
public int fun1() {
return a;
}
}
class Subject2 extends Subject1 {
private int b = 5;
public int fun2() {
return a/b;
}
}
class Example{
public static void main(String[] arags) {
Subject2 sub = new Subject2();
System.out.println(sub.fun1());
System.out.println(sub.fun2());
}
}
답 : 1000
200
풀이 :
Subject2는 Subject1을 상속 받음
Subject2는 부모로부터 물려받은 멤버 변수 a와 fun1 메서드를 사용할 수 있다
sub 인스턴스를 Subject2의 형태로 생성
sub.fun1(); 부모의 fun1을 호출하여 1000을 출력
sub.fun2(); 자식의 fun2를 호출하여 1000/5 = 200을 출력하게 됨
3.
class A {
A() { System.out.printf("%d", 10);
}
class B extends A {
B(int a) { System.out.printf("%d",a);
}
class C extends B {
C(int a) {
super(a/10); //부모 생성자 명시적 호출
System.out.printf("%d", a);
}
}
class Test {
public static void main(String main[]) {
A b = new C(1000); //A의 형태로 C 생성
}
}
답 : 10 100 1000
풀이 :
C 클래스는 B 클래스를 상속받았고, B 클래스는 A 클래스를 상속받았기 때문에 C 클래스의 조상은 A 클래스, B 클래스 모두 해당
부모의 형태로 자식을 생성
생성자는 무조건 상위 클래스로부터 실행을 하게 됨
C 클래스에서 명시적으로 부모의 생성자를 호출
B 클래스에서는 자신의 부모를 명시적으로 호출하지 않는데, 이럴 때는 부모의 인자 없는 생성자를 호출하게 됨
A 클래스의 생성자부터 실행시켜서 10이 출력되고, B 클래스의 생성자 100이 출력되고, C 클래스에서 1000을 출력하게 됨
4.
class Super {
Super() {
System.out.print('A');
}
Super(char x) {
System.out.print(x);
}
}
class Sub extends Super {
Sub() {
Super();
System.out.print('B');
}
Sub(char x) [
this();
System.out.print(x);
}
}
class Test {
public static void main(String[] args) {
Super s1 = new Super('C');
Super s2 = new Sub('D');
}
}
답 : CABD
풀이 :
Super의 형태로 s1 인스턴스를 생성하고, 인자 있는 생성자를 호출
Super 상속관계가 없기 때문에 인자 있는 생성자에서 인자로 받은 C를 출력
Super의 형태로 Sub를 호출하게 되면 일단 SUb의 인자 있는 생성자부터 찾아감 (명시적 호출 확인용)
Sub의 인자 있는 생성자는 this();를 호출하고 this();의 의미는 Sub 클래스의 인자 없는 생성자를 찾아가라는 의미
Sub의 인자 없는 생성자를 찾아갔더니, Super의 인자 없는 생성자를 명시적으로 호출하고 있고, A를 출력하게 됨
부모가 끝나면 직전에 생성자를 수행한 Sub의 인자 없는 생성자로 돌아가서 B를 출력
마지막으로 Sub의 인자 있는 생성자에서 인자로 받은 D를 출력하게 됨
5.
class A {
int a = 10;
public A() {
System.out.print("가");
}
public A(int x) {
System.out.print("나");
}
public static void main(String[] args) {
B b1 = new B();
A b2 = new B(1);
System.out.print(b1.a + b2.a);
}
}
class B extends A {
int a = 20;
public B() {
System.out.print("다");
}
public B(int x) {
System.out.print("라");
}
}
답 : 가다가라30
풀이 :
B 클래스의 형태로 b1v 인스턴스를 생성
B 클래스의 인자 없는 생성자를 먼저 찾아가고, B의 생성자는 명시적으로 부모의 생성자를 호출하지 않기 떄문에 묵시적으로 부모의 생성자를 호출
부모의 인자 없는 생성자에서 '가'를 출력
B의 인자 없는 생성자로 돌아와서 '다'를 출력
A 클래스의 형태로 b2 인스턴스를 생성
부모의 형태로 자식을 생성했기 때문에 자식 클래스의 생성자부터 찾아가게 됨
B 클래스의 인자 있는 생성자에서 부모를 명시적으로 호출하지 않기 떄문에 부모의 인자 없는 생성자 '가'를 다시 출력
B의 인자 있는 생성자로 돌아와서 '라'를 출력
b1.a는 자식의 형태이기 때문에 B 클래스에서 가까운 20
b2.a는 부모의 형태이기 떄문에 A 클래스에서 가까운 10, 두 값을 더해서 출력
6.
class Test
{
public static void main(Stirng[] args) {
int x=1, y=2;
double m=3.4 , n=5.6;
int[] p = {10,20,30,40};
System.out.print(sum(m,n) + " ");
System.out.print(sum(x,y) + " ");
System.out.print(sum(p));
}
public static int sum(int a, int b) {
return a+b;
}
public static double sum(double a, double b) {
return a+b;
}
public static int sum(int a[]) {
int total = 0;
for(int i=0; i< a.length; i++)
total += a[i];
return total;
}
}
답 : 9.0 , 3, 100
풀이 :
sum 메서드가 모두 static으로 선언되어 있음
static은 객체를 생성하지 않고, 일반 함수처럼 사용 가능
static으로 선언된 메서드는 상속관계일 때, 하이딩관계에 주의해야 함
7.
class A {
static void f() { System.out.print("1"); }
void g() { System.out.print("2"); }
}
class B extends A {
static void f() { System.out.print("3"); }
void g() { System.out.print("4"); }
}
class C {
public static void main(Stirng args[]) {
A a = new B();
a.f();
a.g();
}
}
답 : 1 4
풀이 :
부모의 형태로 자식의 a 인스턴스를 생성
a.f()는 오버라이딩 되었지만 f() 메서드는 static 형태
static 형태일 경우에는 어떤 형태로 생성되었는지 확인하여 생성된 형태의 메서드를 호출해주게 됨
a.f()는 부모의 메서드를 호출
a.g()는 일반적으로 오버라이딩된 형태이고, 자식의 g() 메서드를 호출
8.
class A {
public void f() { System.out.print("1");
public static void g() { System.out.print("2"); }
}
class B extedns A {
public void f() [ System.out.print("3"): }
}
class C extends B {
public static void g() { System.out.print("4"); }
}
class D {
public static void main(String args[]) {
A obj = new C();
obj.f();
obj.g();
}
}
답 : 32
풀이 :
A(부모)의 형태로 자식 C를 생성
obj.f();는 일반적으로 오버라이딩 된 형태이고, B 클래스에서 재정의했기 때문에 B 클래스의 f() 메서드를 호출
obj.g();는 C 클래스에서 오버라이딩했지만, static한 메서드이기 때문에 A 클래스의 g() 메서드를 호출
9.
class Foo {
public int a =3;
public void addValue(int i) {
a=a+i;
System.out.println("Foo: " +a+" ");
}
public void addFive()[
a+=5;
System.out.println("Foo: " +a+ " ");
}
}
class Bar extends Foo {
public int a = 8;
public void addValue(double i) {
a = a+ (int)i;
System.out.println("Bar: " +a+ " ");
}
public void addFive() {
a+=5;
System.out.println("Bar: "+a+" ");
}
}
class Test {
public static void main(String[] args) {
Foo.f = new Bar();
f.addValue(1);
f.addFive();
}
}
답 : Foo :4
Bar : 13
풀이:
Foo 클래스 형태로 Bar 인스턴스 f를 생성
상속관계에서 addValue(i), addValue(double i)는 두 개의 인자가 다르기 때문에 메서드 오버로딩이다.
addFive()는 메서드 오버라이딩이다.
f.addValue(1);는 정수값을 넘기기 때문에 Foo 클래스의 addValue를 호출
클래스 | Foo | Bar |
a | 4 |
값을 출력하면 Foo:4가 출력
f.addFive(); 는 메서드 오버라이딩이기 때문에 Bar의 addFive()를 호출
클래스 | Foo | Bar |
a | 4 | 13 |
addFive() 메서드가 있는 클래스는 Bar 클래스이고, a 변수는 참조할 때 가까운 멤버를 참조하기 떄문에 8+5=13을 Bar 클래스 a에 대입하게 됨
10.
interface InterfaceA {
public void up();
public void down();
}
class AB implements InterfaceA {
int value = 0;
public void up() {
value++;
}
public void down() {
value--;
}
void printValue(0 {
System.out.println(value);
}
public static void main(String[] args) {
AB ab = new AB();
InterfaceA ia = ab;
ia.up;
ab.printValue();
}
}
답 : 1
풀이 :
인터페이스 InterfaceA를 정의하고, 추상 메서드 up(), down()을 선언
인터페이스는 모든 메서드들이 추상화 되어야 함
AB 클래스는 인터페이스를 상속받아 모든 추상 메서드를 구현
AB 클래스를 이용해 ab 인스턴스를 생성하고, InterfaceA에 대입
AB 클래스는 InterfaceA 인터페이스를 구현하였으므로, 대입이 가능
ia.up();을 이용해 value 값을 1증가시킴
ia와 ab는 모든 같은 객체를 가리키고 있으므로 ab.printVlaue(); 하게 되면 1값이 출력
11.
import java.util*;
class Viest {
public static void main(String[] args) {
Vector v1 = new Vector();
Vector v2 = new Vector();
v1.addElement("java_book");
v2.addElement("java_book");
System.out.println(v1.equals(v2));
System.out.println(v1 == v2);
}
}
답 : true
false
풀이 :
유틸 패키지에 있는 Vector 클래스 v1, v2를 생성
Vector는 배열과 같이 데이터를 저장할 수 있는 공간
v1와 v2에 모두 java_book이라는 데이터를 대입
첫 번째 출력, equlas 메서드는 두 객체가 같은 구조를 가지고 있는지 비교하는 메서드
v1과 v2 모두 Vector 클래스이고, 똑같이 java_book이 들어가 있다
두 인스턴스가 동일한 구조이기 때문에 true를 출력
두 번째 출력, 두 객체를 ==를 이용해서 비교하면 같은 메모리 주소를 참조하고 있는지 여부를 리턴
v1과 v2는 각각의 객체이고, 두 객체는 서로 다른 메모리를 참조하기 때문에 false를 리턴
== 비교 연산자 | - 주소의 값을 비교 (Call By Reference) |
equals() 메소드 | - 객체끼리 내용 비교 (Call By value) |
12.
class Student {
int id;
char name;
static int count = 0;
Student() {
count++;
}
}
class Studenttest {
public static void main(String[] args) {
Student man1 = new Student();
Student man2 = new Student();
Student man3 = new Student();
Studnet man4 = new Student();
System.out.println(Student.count);
}
}
답 : 4
풀이 :
Student 클래스에는 id, name 멤버변수가 있고, count라는 static한 변수가 있음
static 변수는 인스턴스가 각자 가지고 있는 것이 아니라 공유하는 변수
Student 클래스의 인스턴스 man1을 생성하면 man1은 id, name을 고유하게 가지고 count 공간을 공유
생성자를 통해서 count를 증가시켜 count 값은 1이 됨
man2,3,4도 마찬가지로 count 영역은 공유하고 있기 때문에 count의 최종값은 4가 됨
13.
System.out.println("5+2=" + 3+4);
System.out.println("5+2=" +(3+4));
답 : 5+2 =34
5+2 = 7
풀이 :
java에서 출력문은 문자열을 계속 붙여서 출력해주게 됨
첫 번째 출력에서 5+2 =을 출력한 후 3+4 연산을 수행하지 않고, 하나씩 출력하여 5+2 = 34가 출력
두 번째 출력에서 5+2= 을 출력한 후 3+4를 먼저 연산을 하기 때문에 5+2= 7이 출력됨
'자격증 > 정보처리기사' 카테고리의 다른 글
[c언어] 문제 풀이 (0) | 2023.09.29 |
---|---|
[소프트웨어 구축] 1. 소프트웨어 공학 개념 (0) | 2023.09.27 |