jineecode
프로그래밍 언어 활용 오답노트 본문
1.
#include <stdio.h>
void main(){
int i=1;
for( ; i<10; ){
switch(i%2){
case 0 : printf("짝수: %d\n", i); break;
default : printf("홀수: %d\n", i);
}
i+=3;
}
}
정답)
홀수: 1
짝수: 4
홀수: 7
프로그래밍에서 break는 현재 위치한곳에 적용됩니다. 현재 switch~case 문 안에 있기 때문에 switch~case에만 적용됩니다. for문에 break 효과를 내고 싶으면 switch~case 밖에 break를 써주시면 됩니다.
break;의 위치가 중요한데, for문 안에 switch~case가 있습니다. switch~case 안에 쓴 break;문은 switch~case를 탈출하는 것이지 그 밖에 있는 for문에 대해 break;를 수행하지 않습니다.
오히려 switch~case문 안에 break;를 빼버리면
홀수: 1
짝수: 4
홀수: 4 <-- break문이 없어서 switch~case를 빠져나가지 못해 아래 printf를 실행해버립니다.
홀수: 7
이렇게 출력됩니다.
[출처] [2020년 제3회 기사 실기 출제예상 문제] (10과목) 프로그래밍 언어 활용 - 106 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 두음쌤
2.
#include <stdio.h>
#define ROW 3
#define COL 2
void main( ){
int i, j;
int a[ROW][COL] = {{1, 2}, {3, 4}, {5, 6}};
int sum = 0;
for(i=0; i<ROW; i++){
for(j=0; j<COL; j++){
sum += a[i][j];
}
}
printf("%.2f", (float)sum/(ROW*COL));
}
쌤
정답) 3.50
해설) #define과 소수점 출력 관련해서 문제를 출제하였습니다.
#define ROW 3의 의미는 소스 코드 내에서 ROW라고 정의되어 있는 부분을 3으로 바꾸겠다는 의미입니다. 그럼 #define COL 2는 COL이라고 정의되어 있는 부분을 2로 바꾸겠다는 의미겠죠.
그럼 아래와 같은 소스코드와 완전히 동일합니다.
#include <stdio.h>
void main( ){
int i, j;
int a[3][2] = {{1, 2}, {3, 4}, {5, 6}};
int sum = 0;
for(i=0; i<3; i++){
for(j=0; j<2; j++){
sum += a[i][j];
}
}
printf("%.2f", (float)sum/(3*2));
}
이차원 배열
int a[3][2] = {{1, 2}, {3, 4}, {5, 6}};
을 풀어쓰면
a[0][0] = 1;
a[0][1] = 2;
a[1][0] = 3;
a[1][1] = 4;
a[2][0] = 5;
a[2][1] = 6;
와 같습니다.
이중 for문을 돌게 되면 sum은 3*2 사이즈 이차원 행렬안의 모든 요소 값의 합이 되고 1+2+3+4+5+6=21이 됩니다.
sum=21
printf("%.2f", (float)sum/(3*2));
printf("%.2f", (float)21/6);
마지막 printf에서 %.2f의 의미가 중요한데, %f는 실수를 출력하는 것입니다. 여기에 .2라고 붙이면 소숫점 뒤에 2자리를 출력하라는 의미가 됩니다. 그렇기 때문에 (float)21/6=3.50000가 되는데 소수점 2자리를 출력해야 하므로 3.50이 됩니다.
[출처] [2020년 제3회 기사 실기 출제예상 문제] (10과목) 프로그래밍 언어 활용 - 110 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 두음쌤
3.
#include <stdio.h>
int main()
{
int a = 10;
int *p = &a;
printf("%d %d\n", a, *p);
a = 30;
printf("%d %d\n", a, *p);
return 0;
}
답)
10 10
30 30
해설에 앞서 이번 문제는 비전공 이신분들에게 다소 어려운 문제임을 말씀 드립니다
C언어의 포인터는 전공자들도 C언어를 포기하게 만들어 버리는 무시무시한 놈인데요
정보처리 기능사 시험에 유사 문제가 출제가 되었기에
기사에도 나올 가능성이 있어서 데일리 문제로 출제하였습니다
아마도 기사 문제도 기능사와 유사하거나 약간 더 어려운 수준으로 나올수 있을꺼 같네요
해설)
int a = 10; 을 하게 되면 4바이트의 정수형 변수 a 를 만들고 10을 assign 합니다 (변수a에 10을 저장)
int *p = &a; 이부분이 바로 포인터 인데요
포인터 변수는 변수명 앞에 별 '*'을 붙입니다
즉, 정수형 포인터 변수 p를 만들고 변수 a의 주소값을 assign 합니다 (a의 주소값을 포인터 변수 p에 저장)
printf("%d %d\n", a, *p); 변수 a에 저장된 10을 %d로 출력 합니다.
그리고 한칸 띄고 포인터변수가 가리키는 변수 a의 값 10을 %d로 출력 합니다
a=30; 에서 a에 있던 10은 날라가고 30이 새로 저장 됩니다
그리고 나서 다시 printf함수로 출력을 합니다
printf("%d %d\n", a, *p); 변수 a에 저장된 30을 %d로 출력 합니다.
그리고 한칸 띄고 포인터변수가 가리키는 변수 a의 값 30을 %d로 출력 합니다
추가해설)
포인터 변수는 주소값을 저장하는 변수 입니다
데이터타입에는 int, long, char, char[] 등 다양하게 있는데요
포인터 변수는 데이터타입은 동일하게 작성하고 위에도 설명 했듯이 변수명 앞에 '*'을 붙입니다
또한 주소값은 위의 예제 처럼 일반 변수명 앞에 '&'를 붙이면 됩니다
그리고 포인터 변수는 printf() 함수에서 출력을 할 때,
값을 출력하는 경우에는 '*'를 붙이고,
주소값을 출력하는 경우에는 '*'을 붙이지 않습니다
더 자세한 참조 사이트: m.blog.naver.com/PostView.nhn?blogId=highkrs&logNo=220172673948&proxyReferer=https:%2F%2Fwww.google.com%2F
[출처] [2020년 제3회 기사 실기 출제예상 문제] (10과목) 프로그래밍 언어 활용 - 124 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 보안쌤
4.
Parent.java
public class Parent {
String className = "Parent Class";
public void info() {
System.out.println( className );
}
}
Child.java
public class Child ( ① ) Parent {
String className = "Child Class";
public void info() {
super.info();
System.out.println( className );
}
}
Main.java
public class Main {
public static void main(String args[]) {
Parent p = ( ② ) Parent();
p.info();
Child c = ( ② ) Child();
c.info();
}
}
출력결과
Parent Class ( ③ ) Child Class |
답)
①__________
②__________
③__________
답)
① extends
② new
③ Parent Class
해설)
Parent.java
Parent클래스는 부모 클래스이다.
Child.java
Child클래스는 자식 클래스이다.
Child클래스는 Parent클래스를 상속 받는다
상속은 extends 키워드를 사용한다.
super는 부모클래스 접근할때 사용한다.
Main.java
Parent 클래스와 Child 클래스의 객체를 생성하기 위해
new 키워드를 사용한다.
내가 이해한 바는 이렇다.
Main.java에서 main 클래스 함수가 실행,
Main.java
Parent p = new Parent();
p.info();
p.info() 호출
Parent.java
String className = "Parent Class";
public void info() {
System.out.println( className );
p.info는 parent class 이며, Parent Class가 출력됨.
다음 코드
Main.java
Child c = new child();
c.info();
c.info()호출
Child.java
public class Child extends Parent {
String className = "Child Class";
public void info() {
super.info(); // 부모클래스의 info()를 호출한다.
System.out.println( className ); // "Child Class"를 출력한다.
}
}
c.info는 child class 이며, parent를 상속(extends)받고 있음.
super.info()는 부모 클래스를 호출. 즉, p.info() 라고 보면 됨.부모클래스의 출력문은 다시
"Parent Class" Parent.java
그 다음
Child.java
System.out.println( className );
Child class의 className을 출력.
[출처] [2020년 제3회 기사 실기 출제예상 문제] (10과목) 프로그래밍 언어 활용 - 126 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 보안쌤
5.
ICar.java
interface ICar {
void move();
}
ConCar.java
class ConCar ( ① ) ICar {
public void move() {
System.out.println("이동합니다");
}
}
Main.java
class Main {
public static void main(String args[]) {
ICar car = new ConCar();
car.move();
}
}
답)
① : ( )
실행결과 : ( )
답)
① : ( implements )
실행결과 : ( 이동합니다 )
해설)
ICar.java
인터페이스를 선언한다.
구현몸체는 없이 선언만 존재한다.
ConCar.java
인터페이스는 implements 키워드를 이용한다.
move() 메소드를 실제 구현한다.
Main.java
car.move()는 "이동합니다" 를 출력한다.
[출처] [2020년 제3회 기사 실기 출제예상 문제] (10과목) 프로그래밍 언어 활용 - 128 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 보안쌤
6.
>>> a=10
>>> print(a<<2)
( ① )
>>> print(a>>2)
( ② )
>>> a=5
>>> b=3
>>> print(a&b)
( ③ )
>>> print(a|b)
( ④ )
답)
① 40
② 2
③ 1
④ 7
정답 및 해설)
시프트 연산 '<<', '>>' 은 비트를 이동시키는 연산자이다.
a=10 에서 십진수 10을 이진수로 변환하면 1010이 된다.
a<<2 를 하면 왼쪽으로 2비트 연산을 수행하면 101000 이 된다.
a>>2 를 하면 오른쪽으로 2비트 연산을 수행하면 0010 이 된다.
a=5에서 십진수 5를 이진수로 변환하면 0101이 된다.
b=3에서 십진수 3을 이진수로 변환하면 0011이 된다.
a&b 는 0101 와 0011을 AND 연산을 한다.
0101
AND) 0011
--------------
0001
이진수 0001은 십진수 1이 된다.
* 0 / 0 이면 and 가 0 임을 주의하자
a|b 는 0101 와 0011을 OR 연산을 한다.
0101
OR) 0011
-------------
0111
이진수 0111은 십진수로 7이 된다.
* OR은 두 개 중 하나라도 1이면 1이다.
추가:
두 개를 비교했을 때 서로 다르면 1
쉬프트 오퍼레이터.
=============================================================
[출처] [2020년 제3회 기사 실기 출제예상 문제] (10과목) 프로그래밍 언어 활용 - 131 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 보안쌤
7-1. 생성자와 소멸자
#include <iostream>
using namespace std;
class A{
public:
A( ){
cout << "A" << endl;
};
A(int a){
cout << "B" << endl;
};
~A( ){
cout << "C" << endl;
};
void fn( ){
cout << "D" << endl;
}
};
void main( ){
A a = A(5);
a.fn( );
}
정답)
B
D
C
해설) 클래스 A가 있는데 메서드로 A(), A(int a)가 있습니다. 클래스명과 동일한 이름을 가진 메서드가 생성자입니다.
그리고 ~가 붙어있으면서 클래스 A와 이름이 동일한 ~A() 메서드가 있는데, 이것은 생성자와 정반대의 기능을 하는 소멸자입니다.
main 함수에서 A a = A(5);라고 되어 있기 때문에 A(int a)라는 생성자를 호출하게 되고, B를 출력하게 됩니다.
그 다음 a.fn()은 A클래스의 fn()메서드를 호출하므로 D가 출력이 됩니다.
main함수가 종료되면 a라는 변수가 사라지게 되는데, 이 때 소멸자가 호출이 됩니다.
소멸자가 호출이 되면 ~A()가 불리고, C가 호출되면서 프로그램이 종료하게 됩니다.
생성자는 주로 클래스 내의 변수들을 초기화, 동적 메모리 할당 등을 할 때 사용하고, 소멸자는 주로 클래스 내의 동적할당 되어 있는 메모리들을 해제시킬 때 사용합니다.
6-44
*생성자: 해당 클래스의 객체가 생성될 때 자동으로 호출되는 특수한 종류의 메서드
*소멸자: 객체의 수명이 끝났을 때 객체를 제거하기 위한 목적으로 사용되는 메서드.
- C++에서는 클래스명과 동일한 메서드명을 가지고 '~' 기호를 이용하여 입력값과 반환값이 없다.
- 자바에서는 finalize 라는 메서드를 사용하며 반환값이 없다.
- 파이썬에서는 __del__이라는 메서드명을 사용하고, 첫번째 매개변수에 self를 적어주며, 반환값이 없다.
Q. a.fn()이 없어도 main함수가 끝나게 되면 ~A가 호출되는건가요?
A. 이 코드에서는 fn()과 관련없이 호출됩니다.
소멸자는 변수가 사라지는 순간에 호출됩니다.
A a = A(5);로 선언을 할 때 a라는 변수에 생성이 됩니다.
a가 언제 사라지냐하면 정확히는 해당 블록( '{' ~ '}' 사이)이 끝나면 소멸되어지는데,
간단하게 main함수에서 선언된 변수는 main 함수가 끝나면 사라진다고 생각하시면 됩니다.
사라지는 순간 소멸자가 호출이 되어 C도 출력이 되게 됩니다. fn 호출여부와는 상관이 없습니다.
a.fn()가 없어도 A a = A(5); 코드때문에 변수가 생성되어 메인함수가 끝날시 소멸되기때문에 소멸자가 호출.
[출처] [2020년 제4, 5회 기사 실기 출제예상 문제] (10과목) 프로그래밍 언어 활용 - 145 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 두음쌤
7-2
#include <iostream>
using namespace std;
class A{
public:
A( ){
cout << "A" << endl;
};
A(int a){
cout << "B" << endl;
};
~A( ){
cout << "C" << endl;
};
void fn( ){
cout << "D" << endl;
}
};
void main( ){
A *a = new A(5);
a->fn();
}
정답)
B
D
해설)
A a = A(5);와 A* a = new A(5);의 차이를 알고 계시라고 낸 문제입니다.
int a;라고 하면 정수형 변수를 저장할 수 있는 a라는 이름의 변수가 만들어집니다.
int *a;라고 하면 정수형 포인터를 가리키는 a라는 이름의 포인터 변수가 만들어집니다.
마찬가지로 A a;라고 하면 A클래스를 저장할 수 있는 a라는 이름의 변수가 만들어집니다.
다시 돌아와서 A *a라고 하면 A 클래스를 저장하고 있는 공간을 가리키는 a라는 이름의 포인터 변수가 만들어집니다.
A *a = new A(5);에 대해서 다시 설명을 하면
new A(5);라는 것은 메모리 어딘가에 A클래스에 해당하는 내용(정확히는 인스턴스라고 표현)을 할당합니다.
이 내용의 주소 값을 A *a를 통해 a라는 변수에 저장합니다.
즉, new A(5)로 만들어진 메모리 공간의 주소를 a가 가지고 있는 것입니다.
어쨌든 포인터로 선언하면 new가 선언될 때 생성자가 호출됩니다.
그리고 포인터 변수에 new를 했으면 delete를 해주어야 메모리가 해제됩니다.
해당 코드에서는 delete를 따로 안해주었기 때문에 프로그램이 종료해도 메모리는 할당된 상태가 됩니다.(이걸 메모리 누수라고 합니다.)
만약 코드에서 delete a; 문장이 있었다면 소멸자가 생성되어 어제 데일리 문제 값과 동일하게 나오게 됩니다.
추가로 어제 데일리 문제처럼 일반 변수일 때는 a.fn()으로 메서드 접근을 하고,
오늘 데일리 문제처럼 포인터 변수일 때는 a->fn()으로 메서드 접근을 합니다.
어제와 동일한 결과를 내려면 main 함수가 다음과 같아야 합니다.
void main( ){
A *a = new A(5);
a->fn();
delete a; ///// delete를 해주면 소멸자가 호출됩니다.
}
[출처] [2020년 제4, 5회 기사 실기 출제예상 문제] (10과목) 프로그래밍 언어 활용 - 146 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 두음쌤
8.
#include <stdio.h>
int main()
{
char sTemp[16] = "Hello Sujebi";
printf("%s", &sTemp[6]);
return 0;
}
답) Sujebi
Q. 왜 문자열의 끝까지 출력인가요? 만약 S만 답이라면 코드는어떻게 되야 하는거죠??
A. 포맷 스트링을 바꿔야 겠지요
Q. 그러면 %s를 %c로 바꾸면 S만 출력되는건가요?
A. 그리고 해당 변수도 값을 직접 넣어주어야해요. 주소형태가 아닌 직접적인 값으로요
%s : 문자열
%c : 문자 1개
%d : +-부호 있는 정수
%u : +-부호 없는 정수
%f : 실수
%0.3f : 실수 (소수점 3자리까지 나오게)
%X : 16진수 대문자로
%x : 16진수 소문자로
&가 붙는 이유
9.
#include <stdio.h>
double power(double base, int exp);
int main()
{
printf("%.2f\n", power(2,3));
return 0;
}
double power(double base, int exp)
{
double result = 1;
int n = exp;
while(n--) result *= base;
return result;
}
답) 8.00
정답 및 해설) 지수승을 구하는 프로그램 입니다.
power함수에서 base와 exp를 매개변수로 전달 받아서
while문에서 n값이 1씩 감소하면서 0이 될때까지 반복을 하면서 base를 곱한 결과를 result에 대입 합니다
C언어에는 true, false 가 없고 0이면 거짓, 0이 아니면 참으로 동작
while문 반복이 종료되고 result값을 리턴 합니다
printf함수에서 2의3승인 8을 출력하는데 포맷스트링이 "%.2f" 이므로 8.00을 출력 합니다
[출처] [2021년 제1회 기사 실기 출제예상 문제] (6과목) 프로그램밍 언어 활용 - 6 (수제비- IT 커뮤니티 (정보처리기사,빅데이터분석기사 등)) | 작성자 보안쌤
10.
#include <stdio.h>
#include <stdlib.h> //atoi() 함수 사용하기 위한 헤더파일
int main()
{
char str[8] = "2021"; // 문자열 "2021"
int num = atoi(str); // 문자열을 숫자로 변환
printf("%d", num * 2); // 2021(숫자) * 2 한 값을 출력
return 0;
}
정답) 4042
atoi (A? to Int) - 문자 -> 숫자
itoa (Int to A?) - 숫자 -> 문자
11.
괄호 유무랑 관계 없이 답이 똑습니다.
for문이 있을 때 중괄호가 없으면 바로 밑에 명령어 하나는 for문에 묶인 것으로 처리합니다.
파이썬의 불리언 : 참이면 'True', 거짓이면 'False' 대소문자를 반드시 구별합니다.
자바의 불리언: 참이면 'true', 거짓이면 'false'
c++의 불리언 : 참이면 1, 거짓이면 0 (타입을 불리언으로 바꾸면 true, false가 나옴)
생성자는 부모클래스의 생성자 -> 자식클래스의 생성자가 불립니다.
부모 A
자식 B
문제는 소멸자일 경우인데, 소멸자일 경우 클래스를 어떻게 생성했는지에 따라 다릅니다.
일반적인 소멸자는 자식 소멸자 -> 부모 소멸자 순서로 호출합니다.
A B ~A
A B ~B ~A
업캐스팅이라고 하는데, 상위클래스 포인터변수에 하위클래스로 생성(new)를 하는 경우입니다. 이 때 상위클래스 포인터변수에 해당되는 소멸자가 불리게 됩니다.
'지식 > 정보처리기사' 카테고리의 다른 글
정보처리기사 실기 도움 되었던 사이트 및 강의 (0) | 2021.04.20 |
---|---|
SQL 오답노트 (0) | 2021.04.18 |
파이썬 (0) | 2021.04.17 |
프로그래밍 활용 개행 구분하기 (0) | 2021.04.16 |
웹 사이트에서 프로그래밍 연습하기 (0) | 2021.04.16 |