Template sınıflar ve yapılar, herhangi bir sınıfı, farklı değişken tipleri ile bir arada kullanmak istediğimizde yardımımıza yetişiyor.
Aşağıdaki sınıfı örnek alalım;
#pragma once #include <vector> using namespace std; class TemplateExample { public: bool insert_data(int value) { storage.push_back(value); return true; } bool remove_data(int value) { bool found = false; int i = 0; for (const auto v : storage) { if (v == value) { found = true; break; } i++; } if (found) { storage.erase(storage.begin() + i); return true; } return false; } std::vector<int> getStorage(){ return storage; } private: std::vector<int> storage; };
#include "stdafx.h" #include "TemplateExample.h" #include <iostream> using namespace std; int _tmain(int argc, _TCHAR* argv[]) { TemplateExample te; te.insert_data(1); te.insert_data(2); te.insert_data(3); te.remove_data(2); for (const auto v : te.getStorage()) cout << v << endl; cin.ignore(); return 0; }
Buraya kadar bir sıkıntımız yok. Şimdi farzedelim ki, programımız aynı zamanda string ve char değerlerini depolayan sınıflara da ihtiyaç duyacak. Bu durumda ne yapmamız gerekir? Yukardaki sınıfı kopyalayıp değişken tipini değiştirmeyi düşündüyseniz, hiç zahmet etmeyin. Template anahtar kelimesi burada devreye giriyor. Yukardaki sınıfımızda yapacağımız ufak bir değişiklik, sınıfımızın bütün değişken tipleri ile uyumlu hale gelmesini sağlayacak.
template<typename T> class TemplateExample { public: bool insert_data(T value) { storage.push_back(value); return true; } bool remove_data(T value) { bool found = false; int i = 0; for (const auto v : storage) { if (v == value) { found = true; break; } i++; } if (found) { storage.erase(storage.begin() + i); return true; } return false; } std::vector<T> getStorage(){ return storage; } private: std::vector<T> storage; };
Sınıfımızın üzerinde yazan template<typename T> satırı, sınıfımızın bir generik taslak olduğunu belirtiyor ve sınıfımızı yaratırken T değişken tipine atayacağınız değeri otomatikman bütün sınıfa uyguluyor.
Template sınıfları yaratırken, normal sınıflardan farklı olarak yanına değişken tipi de ekleriz;</pre>
Normal;
TemplateClass normal;
Template;
TemplateClass<char> template;
<> işareti arasında vereceğimiz değişken tipi, sınıfımızın içerisindeki bütün T'lerin yerine geçiyor. Dolayısıyla, başımız ağrımadan bütün değişken tiplerine uyumlu bir depolama sınıfı elde etmiş oluyoruz.
Kullanım;
#include "stdafx.h" #include "TemplateExample.h" #include <iostream> using namespace std; int _tmain(int argc, _TCHAR* argv[]) { // Tamsayı (integer) TemplateExample<int> tamsayiDepolama; tamsayiDepolama.insert_data(1); tamsayiDepolama.insert_data(2); tamsayiDepolama.insert_data(3); tamsayiDepolama.remove_data(2); for (const auto v : tamsayiDepolama.getStorage()) cout << v << endl; // Karakter(char) TemplateExample<char> charDepolama; charDepolama.insert_data('a'); charDepolama.insert_data('b'); charDepolama.insert_data('c'); charDepolama.remove_data('b'); for (const auto v : charDepolama.getStorage()) cout << v << endl; // Yazı (string) TemplateExample<std::string> stringDepolama; stringDepolama.insert_data("this"); stringDepolama.insert_data("is"); stringDepolama.insert_data("sparta!"); stringDepolama.remove_data("is"); for (const auto v : stringDepolama.getStorage()) cout << v.c_str() << endl; cin.ignore(); return 0; }
Template anahtar kelimesi, yalnızca struct ve classlara özgü değildir. Aynı zamanda fonksiyon tanımlamalarınızda da bu anahtar kelimeyi kullanabilirsiniz. Örnek olarak ;
template<typename T> void TemplateFonksiyon(T val) { return; }
TemplateFonksiyon<int>(1);
No comments:
Post a Comment