fullstack

[JSP] JSP Scripting

Web

JSP의 스크립팅 요소(Scripting Element)에 대해 알아보자.




- 지시문 (Directive)


JSP 엔진 및 컨테이너에게 현재의 페이지 처리와 관련된 정보를 전달하는 목적으로 활용한다.

<%@ 와 %> 사이에 코드를 위치하여 사용한다.


1
<%@page contentType="text/html;charset=utf-8"%>





- 스크립트릿 (Scriptlet)


JSP가 강력한 이유이다. JSP 페이지 내에 Java 코드를 넣을 수 있다.

<% 와 %> 사이에 코드를 위치하여 사용한다.


1
2
3
4
5
<%
    for (int i=0; i<=10; i++) {
        out.println(i+"<bt/>");
    }
%>





- 표현식 (Expression)


간단한 데이터를 출력하기 위해 사용한다.

<%= 와 %> 사이에 코드를 위치하여 사용한다.


1
<%= result%>





- 선언 (Declaration)


JSP 페이지 전체에서 사용할 변수나 메소드 등을 선언한다.

<%! 와 %> 사이에 코드를 위치하여 사용한다.


1
2
3
4
5
6
<%!
    String text = "Hello World";
    public boolean isExist() {
        return true;
    }
%>





- 주석


코드 상에 설명을 덧붙이기 위해 사용한다.

<%-- 와 --%> 사이에 설명을 쓴다.


1
<%-- Comment --%>



[C] call by value & call by reference

Language/C

함수를 호출할때 매개변수의 형태에 따라 call by value(값에 의한 호출)와 call by reference(참조에 의한 호출) 두가지의 방식이 있다.

두방식의 차이에 대해 알아보자.




- call by value


call by value는 값에 의한 호출로 매개변수에 값을 복사해 넘겨주는 방식이다.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#include <stdio.h>
 
int square(int num)
{
    return num*num;
}
 
int main()
{
    int n = 10;
    printf("%d\n", n);

    n = square(n);
    printf("%d\n", n);

    return 0;
}



위의 예제에서처럼 call by value는 매개변수에 값을 복사해서 전달해야되기 때문에 인자를 넘겨줄 때 마다 메모리 공간을 할당해 비용이 발생한다는 단점이 있다.

단, 원본의 값이 변경될 가능성이 없다는 장점을 가지고 있다.



- call by reference


call by reference는 참조에 의한 호출로 값을 복사하지 않고, 주소값을 인자로 전달하는 방식이다.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#include <stdio.h>
 
void square(int *num)
{
    *num = (*num)*(*num);
}
 
int main()
{
    int n = 10;
    printf("%d\n", n);

    square(&n);
    printf("%d\n", n);

    return 0;
}



위의 예제에서 처럼 call by reference는 매개변수에 값을 복사하지 않고, 주소값을 인자로 전달해 call by value의 고비용 문제를 해결하였다.

단, call by value와 반대로 원본의 값이 변경될 가능성이 있다는 단점을 가지고 있다.


[Unity3D] WWW객체로 Web에 있는 Image 불러오기

Unity

Web에 있는 이미지를 불러오기 위해 WWW객체를 사용한다.

WWW객체는 URL의 내용을 가져오기 위한 유틸리티 모듈이다.


1
2
3
4
5
6
7
public string url = " /* Image url  */ ";
IEnumerator Start()
{
    WWW www = new WWW(url);
    yield return www;
    plane.GetComponent<Renderer>().material.mainTexture = www.texture;
}



Web에 있는 이미지를 불러와 plane에 적용하였다.

[C++] 상속 (Inheritance)

Language/C++

- 상속의 기본 개념


현실 세계에서 부모의 재산을 물려받는 상속과 비슷하게 객체지향에서의 상속은 다른 클래스의 모든 멤버를 물려 받아 지니고 있게 되는 것을 말한다.

이때 상속되는 클래스를 'Base 클래스' 라고 하며, 상속하는 클래스를 'Derived' 클래스라한다. 다른 표현으로 다른 표현으로 부모 클래스와 자식 클래스 혹은 Super 클래스와 Sub 클래스 라고도 한다.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
class AAA
{
public:
    void funcA() { cout << "AAA" << endl; }
};
 
class BBB : public AAA
{
public:
    void funcB() { 
        funcA();
        cout << "BBB" << endl;
    }
};



위 코드에서 7번째 줄을 보면 콜론(:)을 이용하여 BBB 클래스가 AAA클래스를 public 상속한 것을 볼 수 있다.

따라서 AAA 클래스의 멤버 함수인 funcA를 BBB클래스에서 자유롭게 쓰고 있는 것을 볼 수 있다.




- 상속하는 클래스의 객체 생성 및 소멸 순서


객체의 생성과 소멸순서를 알아보기 위해 다음과 같이 출력을 해보았다.


1
2
3
4
5
6
7
8
9
10
11
12
13
class AAA
{
public:
    AAA() { cout << "AAA Constructor" << endl; }
    ~AAA() { cout << "AAA Destructor" << endl; }
};
 
class BBB : public AAA
{
public:
    BBB() { cout << "BBB Constructor" << endl; }
    ~BBB() { cout << "BBB Destructor" << endl; }
};




위와 같이 생성자는 Base 클래스가 먼저 출력되고 소멸자는 반대로 출력되는 것을 볼 수 있다.

소멸자는 반대로 호출되는 이유는 메모리의 완벽한 해제를 위해서이다.


여기서 중요한것은 생성자가 호출되는 과정인데, 출력만 보면 AAA 클래스의 생성자가 먼저 호출되고 BBB 클래스의 생성자가 호출되는 것 같지만, 사실은 그 반대다.

BBB 클래스의 생성자가 먼저 호출되고 몸체부분은 실행되지 않는다. 다음으로 AAA 클래스의 생성자가 실행되고 나서야 BBB의 몸체부분이 실행되는 것이다.

이걸 제대로 이해한다면 멤버 이니셜라이저(member initializer)를 이용하여 Base 클래스에서 인자가 존재하는 생성자를 올바르게 초기화 할 수 있다.


1
2
3
4
5
6
7
8
9
10
11
12
13
class AAA
{
    int valA;
public:
    AAA(int _val) { valA = _val; }
 
};
 
class BBB : public AAA
{
public:
    BBB(int _val) : AAA(_val) {}
};



12번째 줄에서 멤버 이니셜라이저를 통해 AAA 클래스의 인자가 있는 생성자를 호출하였다.




- public, protected, private 상속


기본적으로 public 상속을 많이 사용하지만 세가지 형태의 상속이 존재한다.

이 상속 형태에 따라 Base 클래스의 멤버가 Derived 클래스로 상속되는 과정에서 접근 권한이 변경된다.

상속되는 과정에 따른 접근 권한 변경은 아래와 같다.



'Language > C++' 카테고리의 다른 글

[C++] 객체 포인터  (0) 2015.12.22
[C++] 상속의 조건. is-a 와 has-a  (0) 2015.12.19
[C++] mutable 키워드  (0) 2015.12.03
[C++] explicit 키워드  (0) 2015.12.02
[C++] static 키워드  (0) 2015.12.02

[C++] mutable 키워드

Language/C++

원래대로라면 const로 멤버 함수가 상수화되면 이 함수는 멤버 변수를 변경시키지 못한다. 그러나 멤버 변수가 mutable로 선언되어 있다면 상수화된 멤버 함수라도 멤버 변수 변경이 가능해진다.

mutable 선언은 되도록 사용하지 않는 것이 좋다고 한다. 어쩔수 없는 경우라면 차라리 함수를 상수화하지 않는 것이 더 나을 수 있다.

아래는 mutable 키워드 사용 예이다.


1
2
3
4
5
6
7
8
9
class AAA
{
    mutable int val;
public:
    void setValue(int _val) const
    {
        val = _val;
    }
};



setValue는 상수화된 멤버 함수이므로 원래대로라면 멤버 변수 val을 변경할 수 없지만 val 이 mutable로 선언되었으므로 값 수정이 가능하다.


'Language > C++' 카테고리의 다른 글

[C++] 상속의 조건. is-a 와 has-a  (0) 2015.12.19
[C++] 상속 (Inheritance)  (0) 2015.12.03
[C++] explicit 키워드  (0) 2015.12.02
[C++] static 키워드  (0) 2015.12.02
[C++] const 키워드  (0) 2015.12.02

[C++] explicit 키워드

Language/C++

explicit 키워드는 생성자 앞에 붙여 묵시적인 호출을 허용하지 않을 때 사용 된다.

즉 객체 생성 관계를 분명히 하고자 할 경우 사용하며, 모든 생성자의 explicit 키워드를 붙이는 프로그래머도 많다.

아래는 explicit 키워드 사용 예이다.


1
2
3
4
5
6
7
8
9
10
11
12
13
class AAA
{
public:
    explicit AAA(int n) { cout << n << endl;}
};
 
int main()
{
    AAA a1(10);
    AAA a2 = 10// error
 
    return 0;
}



AAA a2 = 10; 은 묵시적으로 AAA a2(10)  으로 변환되나 explicit 키워드로 묵시적인 호출을 허용하지 않았으므로 에러가 나타난다.


'Language > C++' 카테고리의 다른 글

[C++] 상속 (Inheritance)  (0) 2015.12.03
[C++] mutable 키워드  (0) 2015.12.03
[C++] static 키워드  (0) 2015.12.02
[C++] const 키워드  (0) 2015.12.02
[C++] 복사 생성자  (0) 2015.12.02

[C++] static 키워드

Language/C++

C언어에서 static 키워드는 지역 변수에 붙여 전역 변수의 특징을 지니게 하는데 사용되었다.

하지만 객체지향에서는 전역 변수, 전역 함수라는 개념이 존재하지 않는다. 따라서 이를 대처하기 위해 static 멤버라는 개념이 등장하였다.

다음은 static 멤버 사용 예이다.


1
2
3
4
5
6
7
8
class AAA
{
    static int count;
public:
    AAA() { cout << count++ << "번째 객체 생성." << endl; }
};
 
int AAA::count = 1;



static 멤버는 main함수가 호출되기도 전에 메모리 공간에 올라가 초기화되므로 public으로 선언이 된다면 객체 생성 이전에도 접근이 가능하다.

또한 객체의 멤버로 존재하는 것이 아니라 선언되어 있는 클래스 내에서 직접 접근할 권한이 부여된 것 뿐이다.


'Language > C++' 카테고리의 다른 글

[C++] mutable 키워드  (0) 2015.12.03
[C++] explicit 키워드  (0) 2015.12.02
[C++] const 키워드  (0) 2015.12.02
[C++] 복사 생성자  (0) 2015.12.02
[C++] friend 선언  (0) 2015.12.02

[C++] const 키워드

Language/C++

const 키워드는 어디에 사용하는가에 따라 다양하게 활용된다.




- const 키워드 기본


const 키워드의 가장 기본적인 사용 3가지는 아래와 같다.



1. 변수를 상수화 한다.


1
2
const int a = 10;
= 20// error



2.  포인터가 가리키는 데이터를 상수화 한다.


1
2
3
int a = 10;
const int* pa = &a;
*pa = 20// error



3. 포인터 자체를 상수화 한다.


1
2
3
4
int a = 10;
int b = 20;
int* const pa = &a;
pa = &b; // error





- 멤버 이니셜라이저 (member initiallizer)


클래스에서 변하지 않는 상수로 멤버변수를 초기화 하고 싶을 때가 있다. 하지만 const로 멤버 변수를 선언 후 생성자에서 조작하려고 할 경우 이미 쓰레기값을 초기값으로 상수화 되었기 때문에 생성자를 통한 초기화를 사용할 수 없다. 

이럴 때 사용하는 것이 멤버 이니셜라이저라는 문법이다. 이것을 사용하면 const 멤버 변수를 초기화할 수 있다.

 

1
2
3
4
5
6
7
8
9
10
class Info
{
    const int id;
    int password;
public:
    Info(int _id, int _password) : id(_id)
    {
        password = _password;
    }
};



위와같으 콜론(:)을 이용하여 const 멤버변수를 초기화 할 수 있으며 콤마(,)를로 구분지어 여러 const 멤버 변수를 초기화 할 수 있다.




- const 멤버 함수


멤버 함수를 선언할 때 const 키워드를 붙여 멤버 함수를 상수화 할 수 있다.

멤버 함수가 상수화되면 이 함수를 통해서 멤버 변수의 값이 변경되는 것은 허용되지 않는다.

다음과 같이 사용할 수 있다.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
class Info
{
    const int id;
    int password;
public:
    Info(int _id, int _password) : id(_id)
    {
        password = _password;
    }
 
    void showData() const
    {
        cout << "id: " << id << endl;
        cout << "password: " << password << endl;
    }
};



이렇게 사용하면 showData라는 정보를 출력해주기만 하는 함수에서 프로그래머의 실수로 멤버 변수의 값을 변경하는 것을 방지할 수 있다.

또한, 상수화된 함수는 상수화되지 않은 함수의 호출을 허용하지 않을 뿐만 아니라, 멤버 변수의 포인터를 리턴하는 것도 허용하지 않는다.




- const 객체


객체또한 생성과 동시에 상수화 하는 것이 가능하다.

객체가 상수화되면 멤버변수의 조작이 불가능해지며, 상수화된 멤버 함수만 호출이 가능해진다.


1
const AAA a;





- const 키워드를 써야하는 이유


const 키워드는 쓰나 안쓰나 동작은 똑같기 때문에 별로 필요없다고 생각할 수 있으나, 프로그래머의 실수를 줄여주고 프로그램의 안정성을 높여준다.

만약 프로그래머의 실수로 잘못된 코드가 들어갔지만 컴파일에는 이상이 없어 에러메세지를 받을 수 없다면 이는 매우 치명적이다.

그러므로 프로그램을 작성할때 const 키워드를 가급적 많이 사용하는 것이 좋다.


'Language > C++' 카테고리의 다른 글

[C++] explicit 키워드  (0) 2015.12.02
[C++] static 키워드  (0) 2015.12.02
[C++] 복사 생성자  (0) 2015.12.02
[C++] friend 선언  (0) 2015.12.02
[C++] this 포인터  (0) 2015.12.02

[C++] 복사 생성자

Language/C++

- 복사 생성자란


복사 생성자란 자기 자신과 같은 형태의 객체를 인자로 받을 수 있는 생성자를 말한다.


다음은 복사 생성자의 예이다.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
#include <iostream>
using namespace std;
 
class AAA
{
    int val;
public:
    AAA(int _val) {
        val = _val;
    }
    AAA(const AAA& a) {
        val = a.val;
    }
    void showValue() { cout << "value: " << val << endl; }
};
 
int main()
{
    AAA a1(10);
    AAA a2(a1);
 
    a1.showValue();
    a2.showValue();
 
    return 0;
}




복사생성자는 인자로 전달된 객체를 레퍼런스로 받아야 하며 내용 변경을 불가능 하게 하기 위해 const 선언을 한다.




- 다폴트 복사 생성자


일반 생성자와 소멸자처럼 복사 생성자도 디폴트 복사 생성자를 제공한다.

위 예제에서 11~13 라인을 지워도 자동으로 디폴트 복사 생성자를 삽입하기 때문에 똑같이 동작한다.


하지만 생성자내에서 동적할당을 하는경우 디폴트 복사 생성자에서는 얕은 복사(Shallow Copy)를 하게 되는데 이경우 문제가 발생한다.

따라서 깊은 복사(Deep Copy) 로 직접 복사 생성자를 구현해 주어야 한다.


'Language > C++' 카테고리의 다른 글

[C++] static 키워드  (0) 2015.12.02
[C++] const 키워드  (0) 2015.12.02
[C++] friend 선언  (0) 2015.12.02
[C++] this 포인터  (0) 2015.12.02
[C++] 생성자(Constructor)와 소멸자(Destructor)  (0) 2015.11.30

[C++] friend 선언

Language/C++

friend는 말그대로 친구를 말한다. 친구에게는 모든것을 허용해야 한다.

클래스안에서 private로 선언된 멤버변수는 외부 접근이 허용되지 않는 것이 원칙이다. 하지만 friend 선언을 통해서 접근을 허용할 수 있다.




- 전역 함수에 대한 friend 선언

 

1
2
3
4
5
6
7
8
9
10
11
class AAA
{
    int val;
public:
    friend void setValue(AAA& a, int val); // friend 선언
};
 
void setValue(AAA& a, int val)
{
    a.val = val;
}



원래대로라면 전역 함수 setValue에서 AAA객체의 val값에 접근할 수 없다.

하지만 5번째줄에서 friend 선언을 했으므로 접근이 허용되었다.




- 클래스에 대한 friend 선언

 

1
2
3
4
5
6
7
8
9
10
11
12
13
class AAA
{
    int val;
    friend class BBB;
};
 
class BBB
{
public:
    void setValue(AAA& a, int val) {
        a.val = val;
    }
};



클래스도 마찬가지로 friend 선언을 하면 private영역의 접근을 허용한다.

주의할 것은 friend 선언은 단방향적으로 AAA 클래스가 BBB 클래스에게 접근을 허용한 것이지 BBB 클래스또한 AAA 클래스에게 접근을 허용한 것은 아니다.




friend 선언은 매우 편리하지만 객체지향에서 중요시하는 '정보 은닉'을 해치는 경우를 초래할 수도 있으니 너무 많은 남발은 하지 않는 것이 좋다.


'Language > C++' 카테고리의 다른 글

[C++] const 키워드  (0) 2015.12.02
[C++] 복사 생성자  (0) 2015.12.02
[C++] this 포인터  (0) 2015.12.02
[C++] 생성자(Constructor)와 소멸자(Destructor)  (0) 2015.11.30
[C++] 캡슐화 (EnCapsulation)  (0) 2015.11.30