KarelOOP2

Retired DISLab
이동: 둘러보기, 찾기

목차

개요

Karel은 자바로 프로그래밍을 처음 배우는 학생들을 교육하기 위한 목적으로 스탠포드 대학에서 만든 라이브러리이다. 그런데 기존 Karel 라이브러리는 클래스, 추상 클래스, 인터페이스 등을 배우기에 부족함이 있어 KarelOOP2는 Karel 라이브러리에 필요한 코드를 추가한 것이다.

자바의 장단점

자바의 장점

자바는 다른 언어와 비교해서 다음과 같은 장점이 있다.

  1. 객체지향개념을 충실히 반영하고 있다.[1]
  2. 메모리를 직접 다루는 포인터 대신에 레퍼런스를 지원하여 메모리 참조를 잘못해서 발생하는 오류를 줄일 수 있다.[2]
  3. 프로그래머가 메모리에 만든 객체를 명시적으로 적지 않아도 가비지(garbage)가 되면 자비지 수집기(garbage collector)가 자동으로 메모리에 사용하지 않는 메모리를 반환한다.[3]
  4. 자바 가상기계(JVM; Java Virtual Machine)에서 실행되기 때문에 바이트코드 수준에서 호환성이 있다.[4]
  5. 스레드를 언어에서 기본적으로 제공하여, 스레드 프로그램을 작성하는 방법이나 동작 등에 일관성이 있다.[5]
  6. 한 클래스에 속한 모든 코드는 클래스 내부에 모두 기술하여야 할 뿐만 아니라, 하나의 파일에 모두 기술하여야 한다. 그러므로 코드를 읽기가 쉽다.
  7. 안드로이드 스마트 폰에서 기본 언어로 자바가 채택되었다.[6]

자바를 배울 때 어려운 점

자바는 처음 배우는 학생들에게 다음과 같은 어려움이 있다.

  1. 프로그램이 처음 시작하는 메소드인 main이 클래스 내부에 정의되어 있다.
  2. GUI 프로그램을 작성하는데 어려움이 있다. 그 이유는 GUI 프로그램을 구성하기 위하여 기본적으로 작성해야 하는 코드가 많기 때문이다.

ACM Java Task Force

자바 프로그램을 배울 때 만나는 어려움을 피하고 프로그래밍 자체에 집중하기 위하여 ACM에서 ACM Java Task Force를 만들있다. 이 연구팀에서는 자바를 쉽게 배울 수 있는 클래스 라이브러리와 프로그래밍 작성 스타일을 미국의 여러 대학교와 협력하여 만들고 이를 대학에 보급하였다. Karel은 이 라이브러리를 이용하여 작성되었다.

KarelOOP2

KarelOOP2는 객체지향기법을 이용한 Karel 버전 2이다. 프로그램을 작성하기 위해서 아래 라이브러리를 다운로드 받아서 프로젝트에 포함시켜야 한다.


KarelOOP2 라이브러리는 아래 링크에서 다운로드 받으면 된다.


KarelOOP2 라이브러리의 도움말은 아래 링크를 이용하세요.


KarelOOP2를 이용한 샘플 코드는 아래와 같다.


KarelOOP2 코드의 특징을 다음과 같습니다.

  • onInit() - Start Program 버튼을 누르기 전에 불리는 메소드이다. 즉, 화면에 월드가 나타나면 처음 불리는 메소드이다. Start Program 버튼을 누르기 전에 초기화를 하는 코드를 여기에 작성한다.
  • onStart() - Start Program 버튼을 누르면 실행되는 메소드이다. 기존 버전의 run() 메소드와 동일하다.

각주

  1. 객체지향개념에서 가장 중요한 클래스를 지원한다. 또한 재사용성을 증가시키는 다양한 기법을 제공한다. 먼저 이미 존재하는 코드를 재사용하기 위한 기본적인 기법으로 자바는 다른 객체지향언어와 동일하게 계승을 지원한다. 또한 알고리즘의 재사용성을 증가시키기 위하여 추상 클래스(abstract class)와 추상 메소드를 지원한다. 이 외에도 구현과 인터페이스를 분리하기 위하여 인터페이스(interface)를 지원한다. 이와 더불어 메소드는 C++의 가상 함수(virtual function)처럼 실행시에 해당 객체에 속한 메소드를 호출해주는 동적 바인딩(dynamic binding)을 한다.
  2. C, C++에서는 포인터 변수를 사용할 수 있다. 포인터 변수에 저장되는 것은 메모리 주소인데, 이 메모리 주소는 산술 연산을 통해 주소를 계산한 다음, 이 주소를 포인터 변수에 저장할 수 있다. 이때 계산을 잘못하여 포인터 변수에 저장된 주소가 유효하지 않은 것이라면 심각한 문제가 발생할 수 있다. 첫째 사용하고 있지 않은 혹은 해당 변수의 값을 저장한 곳이 아니 메모리를 참조할 경우, 엉뚱한 변수나 위치의 값을 변경할 수 있다. 둘째, 현재 실행중인 프로세스의 메모리 범위(virtual address space)를 벗어난 메모리를 접근할 경우 보안에 문제가 발생할 수 있기 때문에, 운영체제는 이러한 경우 잘못된 연산을 수행한 해당 프로세스를 강제로 종료시킨다. 이러한 메모리 참조를 잘못하여 발생하는 버그는 전체 버그 중에 많은 부분을 차지하기 때문에 자바에서는 포인터를 제공하지 않는다.
  3. 사용자가 임의의 시점에 메모리를 할당하는 방법으로 C에서는 malloc 함수를 제공하고, C++에서는 new 연산자를 제공한다. 예를 들어
    Person* person = (Person*)malloc(sizeof(struct Person)); /* C 스타일 */
    Person* person = new Person(); // C++ 스타일
    

    와 같이 메모리를 할당한다. 이때 C에서는 Person이 구조체(struct)로 정의되었고, C++에서는 클래스로 정의되었다고 가정하자.

    이 메모리가 더 이상 필요없을 경우 C에서는 free 함수를 이용해서 반환하고, C++에서는 delete 연산자를 이용하여 메모리를 반환한다. 이 예는 아래와 같다.

    free(person); /* C 스타일 */
    delete person; // C++ 스타일
    

    만약 free나 delete를 이용하여 반환하지 않는 경우의 예를 통해 메모리 관리에서 발생하는 문제점을 알아보자.

    Person* person = (Person*)malloc(sizeof(struct Person)); /* 객체1*/
    person = (Person*)malloc(sizeof(struct Person)); /* 객체2 */
    

    위 코드에서 객체1을 생성한 후 반환하지 않고 객체2를 동일 변수로 가리키게 되면 객체1은 더 이상 참조할 수 없게 된다. 이 객체는 제거하지 않았기 때문에 이 객체가 차지하는 메모리가 반환되지 않아 메모리에서 공간을 차지하고 있게 된다. 하지만 사용할 수 없는(접근할 수 없는) 메모리로 남게 되어 메모리를 낭비하게 되는 것이며, 이를 메모리 누수(memory leak)가 발생했다고 한다. 메모리 누수가 없도록 하려면 코드를 아래와 같이 작성해야 한다.

    Person* person = (Person*)malloc(sizeof(struct Person)); /* 객체1*/
    free(person); /* 객체1 반환 */
    person = (Person*)malloc(sizeof(struct Person)); /* 객체2 */
    

    객체1과 같이 더 이상 참조할 수 없는 메모리를 가비지(garbage)라고 하며 C, C++와 같은 언어는 명시적으로 해당 메모리를 제거해야 한다. 하지만 자바에서 이 메모리는 자동으로 제거된다. 이러한 제거는 즉시 일어나는 것이 아닐 뿐만 아니라 언제 제거될지 예측할 수 없다. 가비지를 자동으로 제거하는 것을 가비지 수집기(garbage collector)라 부른다. 가비지 수집기가 동작하는 동안에는 프로그램의 실행이 잠시 멈춘다. 이러한 현상은 실시간 프로그램을 작성하는데 장애가 된다. 현재의 JVM은 실시간에 대응하고 성능향상을 위하여 힙 메모리가 부족할 때 가비지 수집기가 실행되고 가비지를 제거하여 필요한 메모리가 확보되면 가비지 제거 작업을 멈춘다. 즉, 한 번에 모든 가비지를 제거하지 않는다.
    다음 코드는 배열과 포인터의 관계에 대한 것이다.

    Person* person = (Person*)malloc(sizeof(struct Person);
    person[1]->name = "홍길동"; // (person + 1)->name = "홍길동" 혹은 (*(person + 1)).name = "홍길동" 과 동일함.
    

    C에서 포인터는 배열과 구분되지 않는다. 그러므로 이와 같은 코드는 컴파일할 때 에러가 발생하지 않지만, 실행하면 배열이 아니기 때문에 엉뚱한 메모리를 참고하게 되는 오류가 발생한다. 이것을 memory leak이라고 한다. Unix나 Linux에서는 segmentation fault가 나거나 엉뚱한 메모리의 값을 변경하게 되는 오류가 발생한다.

  4. C 프로그램을 컴파일하면 특정 머신에서 실행할 수 있는 기계어가 생성된다. 기계어는 CPU 마다 형식이나 명령어 종류가 다르다. 또한 운영체제(OS)에 따라 프로그램을 메모리에 적재(로드)하는 방법이 다르다. 이처럼 CPU와 OS를 합하여 특정 머신이라고 부른다. 예를 들어 PC에서 주로 사용하는 인텔칩에서 실행할 수 있는 기계어와 스마트폰에서 주로 사용하는 ARM 칩에서 실행할 수 있는 기계어 형식이 완전히 다르다. 그러므로 특정 CPU에서 실행할 수 있는 기계어는 다른 CPU에서 실행될 수 없다. 이 뿐만 아니라 동일 CPU를 사용한다고 하더라도 OS가 달라도 생성되는 기계어 코드 형식이 달라진다. 예를 들어 인텔칩을 사용하는 것으로 Windows, Mac, Linux가 있다. 이들 기계에서 실행되는 기계어는 동일한 명령어를 가지고 있지만, 각각의 기계에서 실행되는 기계어 코드가 다른 기계에서 실행되지 않는다. 그 이유는 기계어를 메모리에 로드할 때 사용하는 자료구조나 실행 방법 등에 차이가 있기 때문이다. 즉, 보통 프로그램을 컴파일하면 해당 머신에서 동작하는 기계어가 만들어진다.
    하지만 자바는 특정 머신에 독립적인 기계어가 생성되므로 기존의 기계어와 구분짓기 위해서 자바의 기계어를 바이트코드라고 부른다. 이와 같은 바이트코드를 실행하려면 특정 CPU 뿐만 아니라 특정 OS가 있어야 한다. 이와 같은 기능을 제공하는 것이 JVM(자바 가상기계)이다. 자바 가상기계는 자바 바이트코드를 실행할 수 있는 실행환경인데, OS와 CPU를 프로그램으로 제공한 것입니다.
  5. C는 언어에서 스레드를 위한 키워드를 제공하는 등의 문법을 지원하지 않는다. 그러므로 ptherad와 같은 라이브러리를 이용하여 스레드 프로그래밍을 한다. 이 경우 스레드 라이브러리가 다르면 스레드 프로그래밍 형식도 달라진다. 하지만 자바에서는 문법을 제공하기 때문에 스레드 프로그램을 작성하기도 쉽고 일관성도 있게된 것이다.
  6. 현재는 Kotlin도 지원하고 있음
개인 도구
이름공간
변수
행위
둘러보기
구성원
연구
연구실
기타
도구모음
인쇄/내보내기