반응형
C++은 일반화 프로그래밍
템플릿은 원래 C++ 표준이 아니었고 일반화 프로그래밍 표준이었는데
원래 템플릿 쓰던 애들이 가져와서 C++에서 쓰는거다.
구표준까지는 따로였지만, 신표준으로 넘어가면서 '템플릿도 C++이야' 라고 선언하면서
템플릿이 C++에 흡수되고, 그걸 표준화시킨게 STL(Standard Template Library)다.
얘는 일반화 프로그래밍이라 타입을 정할 수 없다.
1. C++에는 2가지 템플릿이 있다.
1. 템플릿 함수(외부함수를 템플릿으로 만들겠다 이거야)
2. 템플릿 클래스
VS 01_ 코드참고)
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 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 | /* 1. 동적 바인딩에서 Stack and Queue를 Template으로 만들어서 어떤 타입이든 쓸 수 있게 만들어라 */ #define ARR_MAX 2 #define ARR_MIN 0 #include <iostream> #include <string> using namespace std; template <typename T> class vPop { protected: T temp; // Pop 연산을 할 때 리턴할 값을 임시로 저장하는 임시 필드 public: virtual void Pop() = 0; }; template <typename T> class Memory : public vPop<T> { protected: T *arr; // T 타입의 메모리 동적 할당에 쓰이는 포인터 int top; // top과 front는 배열의 위치를 알려주는 카운트 변수이므로 무조건 int public: Memory() // 생성자 { top = -1; arr = new T[ARR_MAX]; } // push and pop operation void Push(T data) { // 만약 메모리가 꽉 찼다면 if (top + 1 >= ARR_MAX) isFull(); // 메모리에 넣을 공간이 있다면 else { system("cls"); cout << "┌───────────────────────┐" << endl; cout << "│Push할 값을 입력하세요.│" << endl; cout << "└───────────────────────┘" << endl; cout << "==> "; cin >> vPop<T>::temp; this->top++; // 탑 변수 이동(ex. from index -1 to index 0) arr[top] = vPop<T>::temp; // 배열에 데이터를 넣음 cout << "-------------------------" << endl; cout << "Push push babay~" << endl; cout << "-------------------------" << endl; } } virtual void Pop() = 0; void isFull() { cout << "-------------------------" << endl; cout << "Hey man~ Memory stack overflow!" << endl; cout << "-------------------------" << endl; } int isEmpty() { if (Memory::top < 0) { cout << "Hey man~ Memory stack underflow!" << endl; cout << "-------------------------" << endl; return 1; } return 0; } }; template <typename T> class MyStack : public Memory<T> { public: MyStack() {} void Pop() { if (!isEmpty()) { // pop한 값을 temp에 넣고 return 한다. // vPop<T>::temp(p[Memory<T>::top]); cout << "Pop한 값 : " << arr[top--] << endl; // return vPop<T>::temp(); } else { return; } } }; //template <typename T> //class MyQueue : public Memory<T> { // T *p; // int front; //public: // // constructor // MyQueue(); // // // setter and getter // void setFront(int front) { this->front = front; } // int getFront() { return this->front; } // // virtual T Pop(); //}; //template <typename T> //MyQueue<T>::MyQueue() //{ // p = NULL; // front = 0; //} //T MyQueue<T>::Pop() //{ // p = Memory<T>::getArr(); // // // pop한 값을 temp에 넣고 return 한다. // if (!isEmpty()) { // temp = p[MyQueue<T>::getFront()]; // // // shift 작업(해야함) // for (T i = 0; i < Memory<T>::getRear(); i++) { // p[i] = p[i + 1]; // } // setRear(getRear() - 1); // // return temp; // } // else { // return -9; // } //} void main() { Memory<string> *mem; MyStack<string> s; string data; // 아래의 변수들은 일종의 스위치이므로 int로 고정 int button; // 자료 구조 버튼 변수 int PushOrPop = 0; // Push or Pop 버튼 변수 int sayYesOrNo = 0; // "계속하시겠습니까?" 버튼 변수 int check = -9; // 예외 처리 false 변수 do { cout << "┌───────────────────────┐" << endl; cout << "│자료 구조를 선택하세요.│" << endl; cout << "└───────────────────────┘" << endl; cout << "1. Stack" << endl; cout << "2. Queue" << endl; cout << "3. Exit" << endl; cout << "-------------------------" << endl; cin >> button; if (button == 1) { mem = &s; } // dynamic binding // else if (button == 2) { mem = &q; } else if (button == 3) { cout << "-------------------------" << endl << "프로그램을 종료합니다." << endl; cout << "빠이루!" << endl << "-------------------------" << endl; return; } else { cout << "-------------------------" << endl << "잘못된 번호를 입력했습니다." << endl; cout << "다시 입력하세요." << endl << "-------------------------" << endl; continue; } system("cls"); cout << "┌─────────────────────────┐" << endl; cout << "│수행할 기능을 선택하세요.│" << endl; cout << "└─────────────────────────┘" << endl; cout << "1. Push Operation" << endl; cout << "2. Pop Operation" << endl; cout << "3. Back to menu" << endl; cout << "-------------------------" << endl; cin >> PushOrPop; switch (PushOrPop) { case 1: mem->Push(data); break; case 2: // pop 연산 mem->Pop(); //cout << "-------------------------" << endl; //if (check != (data = mem->Pop())) //{ // cout << "값 : " << data << endl; // cout << "-------------------------" << endl; //} break; default: break; } cout << "계속하시겠습니까?" << endl; cout << "1. Yes" << "\t" << "2. No" << endl; cout << "-------------------------" << endl; cin >> sayYesOrNo; } while (sayYesOrNo == 1); } | cs |
반응형