programming/C++

[C++] Template 과 iterator 문법 복습하기

KoTiv 2022. 3. 29. 13:58
반응형
SMALL

시작하기에 앞서 Template 와 Iterator란 ? 

Template와 iterator에 대하여 알아보도록 한다.

우선 Template와 Iterator가 무엇인지 알기위해 정의를 해본다면 

Template : 함수나 클래스를 개별적으로 사용하지 않아도, 여러 자료형으로 사용할 수 있게 만들어놓은 틀 ( C언어로 따진다면 strucure같은 느낌이 든다. )

Iterator : Container의 위치값(주솟값)을 저장하는 Point-like oject이다. Container의 자료형에 구애 받지 않는다.

Why using Template & iterator ?

1. template와 iterator는 Generic programming을 하기위해 사용하는 개념이다. 

Generic Programming은 자료형에 독립적인 클래스 혹은 함수를 Specific하게 특정하지 않고 한번의 정의로 다양하게 활용할 수 있는 Programming이다.

 

Template

1.1 Function Template

함수 템플릿이란 함수를 만들때 함수의 기능은 명확하지만 자료형을 모호하게 두는 방식이다.

#include <iostream>
using namespace std;
//정수형 변수 x, y를 받아서 x<y 조건에 맞으면 True, 틀리면 Flase를 return하는 함수이다.
bool less_than(const int x, const int y)
{
return x<y;
}

//만약 int type이 아닌 double type을 받는다면 
bool less_than(const double x, const double y) 
{
	return x<y;
}
// double type에 해당하는 함수를 다시 만들어야 하는 불편함이 존재한다.
int main()
{
	cout<< less_than(2,3) <<endl;
    return 0;
}

위의 방식으로 함수를 만들게 된다면 필요한 데이터 타입에 대한 함수가 없을 시 항상 함수를 새로 정의를 내린이후 함수를 사용 해야한다는 점에서 불편함이 존재한다 . 

하지만 Template를 통하여 정의를 하게 된다면 여러번 다양한 데이터타입에 따라 함수를 재정의하는 번거로운 일이 없어진다.

template<typename T>
bool less_than(const T& x, const T& y) 
{
	return x<y;
}

int main()
{
	cout<< less_than(2,3) << endl;
    cout << less_than(2.4,5.5) << endl;
    return 0;
}

입력 파라미터는 값이 바뀌지 않기때문에 const를 사용하였고 메모리 효율을 높이는 방법으로 return by reference를 사용한 코드이다.

예시를 보며 template를 사용 과정을 살펴보면 

  • 1. template<typename UserType>을 우선 사용하고 
  • 2. 입력 인자 또는 함수의 return type에 해당하는 부분을 UserType으로 바꿔주었다.

만약 인자가 다를경우

template<typename T, typename U>
bool less_than(const T& x, const U& y)
{
	return x< y;
}

int main()
{
	cout<< less_than(2,3) <<endl;
    cout<< less_than(2.4,5.5) << endl;
  	return 0;
}

 

Template function에서 Vector를 인자로 받는 경우

#include <iostream>
#include <vector>

using namespace std;

int sum(vector<int> v)
{
	int res;
    for( int elem: v)
    {
    	res += elem;
    }
    return res;
}

int main()
{
	vector<int> v{1,2,3};
    int res;
    res = sum(v);
    cout<< res << endl;
    return 0;
    
}

위 의 sum 함수를 Template화 한다면 

#include <iostream>
#include <vector>

using namespace std;

template<typename T>
T sum(vector<T> v)
{
	T res;
	for(T elem : v)
    	res += elem;
    return res;
}

int main()
{
	vector<int> v{1,2,3};
    vector<double> v2{1,2,3,4,5,6};
    
    int res1= sum(v);
    int res2 = sum(v2);
    
    cout<< res1 << res2 << endl;
    return 0;
}

예시를 보며 template를 사용 과정을 살펴보면 맨처음 Template사용과 동일하게

  • 1. template<typename UserType>을 우선 사용하고 
  • 2. 입력 인자 또는 함수의 return type에 해당하는 부분을 UserType으로 바꿔주었다.

 

1.2 Class Template

class position{

private:
    int x;
   	int y;
public:
	position(int x, int y)
    void set_axis(int _x, int _Y);
    int getX() const;
    int getY() const;
    void print() const;
};

position::position(int _x, int _y) : x(_x), y(_y) {}

void posiotn::set_axis(int _x, int _y) { x= _x , y= _y; }
int position::getX() const { return x;}
int position::getY() const { retirn y;}
void position::print() const { cout<< x<< ", "<<y << endl; }

int main()
{
	position pt1(1,2);
    prt1.print();
    
    return 0;
}

class를 template로 변형시 

#include <iostream>
#include <vector>
using namespace std;

template <class T>
class position{
private:
    T x;
   	T y;
public:
	position(T x, T y)
    void set_axis(T _x, T _Y);
    T getX() const;
    T getY() const;
    void print() const;
};

template<class T>
position<T>::position(T _x, T _y) : x(_x), y(_y) {}

template<class T>
void posiotn<T>::set_axis(T _x, T _y) { x= _x , y= _y; }
template<class T>
T position<T>::getX() const { return x;}
template<class T>
T position<T>::getY() const { retirn y;}
template<class T>
void position<T>::print() const { cout<< x<< ", "<<y << endl; }

int main()
{
	position<int> pt1(1,2);
    prt1.print();
    
    return 0;
}
  • template<class T>를 써준다 ( class나 typename이나 상관없다 )
  • int과같은 데이터 타입에 해당하는것들을 모두 T로 바꾼다.
  • method가 class 외부에 구현시 template<class T>를 함수 윗줄에 삽입후 범위 지정 연산자 <T>를 삽입해준다.
  • method밖에서 빼놓으면 generic function이기 때문에 template<class T>하나하나 적어준다.
  • main함수에서 객체정의시 class<typename>을 적어준다.

 

iterator

iterator란 컨테이너에 generic하게 작동하는 Point like object라고 한다.

#include <iostream>
#include <vector>

using namespace std;

int main()
{
	int arr[] = {1,2,3};
    int *begin = arr;
    int *end = arr+3;
    for(int* cur = begin; cur!=end ; cur++)
    {
    	cout<< *cur << '\t';
        cout << endl;
    }
	return 0;
}

위으 코드는 포인터를 통하여 container를 순환하는 일련의 예제 코드이다. 

아래의 코드는 iterator 객체를 통하여 container를 순환하는 예제 코드인데 

iterator의 주요 메소드는 v.begin() = begin(v), v.end() = end(v) 이고 주요 연산자는 iter++, iter--, *iter, iter1 != iter2 로볼수 있다.

int main()
{
	vector<int > v{1,2,3};
    auto iter_begin =begin(v);
    auto iter_end = end(v);
    for( auto iter = iter_begin; iter!= iter_end; iter++)
    {
    	cout << *iter << '\t';
        cout <<endl;
    }
    
return 0;
}

auto 연산자는 컴파일러가 데이터형을 알아서 지정해주는 기능을 한다 . 

선언과 동시에 초기화가 진행되야 한다.

 

반응형
LIST