298 lines
10 KiB
C++
298 lines
10 KiB
C++
#include "hack/concepts/concepts.hpp"
|
||
#include "hack/logger/logger.hpp"
|
||
|
||
template<hack::concepts::modern::has_value_type T>
|
||
void example_has_value_type(const T& container)
|
||
{
|
||
/*
|
||
typeid().name() - возвращает декорированное (mangled) имя типа, которое зависит от компилятора:
|
||
i = int (в GCC/G++)
|
||
d = double
|
||
f = float
|
||
c = char
|
||
Ss = std::string (в GCC)
|
||
NSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE = тоже std::string (полное декорированное имя)
|
||
*/
|
||
hack::log()("Value type: ", typeid(typename T::value_type).name());
|
||
}
|
||
|
||
template<hack::concepts::modern::has_key_type T>
|
||
void example_has_key_type(const T& container)
|
||
{
|
||
hack::log()("Key type: ", typeid(typename T::key_type).name());
|
||
}
|
||
|
||
template<hack::concepts::modern::has_mapped_type T>
|
||
void example_has_mapped_type(const T& container)
|
||
{
|
||
hack::log()("Mapped type: ", typeid(typename T::mapped_type).name());
|
||
}
|
||
|
||
template<hack::concepts::modern::has_iterator T>
|
||
void example_has_iterator(const T& container)
|
||
{
|
||
hack::log()("Container is iterable, size: ", std::distance(container.begin(), container.end()));
|
||
}
|
||
|
||
template<hack::concepts::modern::has_size T>
|
||
void example_has_size(const T& container)
|
||
{
|
||
hack::log()("Container size:", container.size());
|
||
}
|
||
|
||
template<hack::concepts::modern::has_key_compare T>
|
||
void example_has_key_compare(const T& container)
|
||
{
|
||
hack::log()("Key compare type: ", typeid(typename T::key_compare).name());
|
||
}
|
||
|
||
template<hack::concepts::modern::has_allocator_type T>
|
||
void example_has_allocator_type(const T& container)
|
||
{
|
||
// Можно получить аллокатор из контейнера
|
||
typename T::allocator_type alloc = container.get_allocator();
|
||
hack::log()("Allocator obtained successfully");
|
||
}
|
||
|
||
// template<hack::concepts::modern::is_string T>
|
||
// void example_is_string(const T& str) {
|
||
// std::cout << "String content: " << str << " (length: " << str.length() << ")" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_sequence_container T>
|
||
// void example_is_sequence_container(const T& container) {
|
||
// std::cout << "Sequence container with " << container.size() << " elements" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_random_access_container T>
|
||
// void example_is_random_access_container(T& container) {
|
||
// if (!container.empty()) {
|
||
// std::cout << "First element: " << container[0] << std::endl;
|
||
// }
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_container_adapter T>
|
||
// void example_is_container_adapter(T& adapter) {
|
||
// std::cout << "Container adapter with " << adapter.size() << " elements" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_associative_container T>
|
||
// void example_is_associative_container(const T& container) {
|
||
// std::cout << "Associative container with " << container.size() << " elements" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_unordered_associative_container T>
|
||
// void example_is_unordered_associative_container(const T& container) {
|
||
// std::cout << "Unordered associative container with " << container.size() << " elements" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_tuple_like T>
|
||
// void example_is_tuple_like(const T& tuple) {
|
||
// std::cout << "Tuple-like with " << std::tuple_size_v<T> << " elements" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_fixed_array T>
|
||
// void example_is_fixed_array(const T& array) {
|
||
// std::cout << "Fixed array with " << std::extent_v<T> << " elements" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_std_array<T, std::tuple_size_v<T>> T>
|
||
// void example_is_std_array(const T& array) {
|
||
// std::cout << "std::array with " << array.size() << " elements" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_any_container T>
|
||
// void example_is_any_container(const T& container) {
|
||
// std::cout << "Any container with " << container.size() << " elements" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_iterable T>
|
||
// void example_is_iterable(const T& iterable) {
|
||
// std::cout << "Iterable object: ";
|
||
// for (const auto& item : iterable) {
|
||
// std::cout << item << " ";
|
||
// }
|
||
// std::cout << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_sized T>
|
||
// void example_is_sized(const T& sized) {
|
||
// if constexpr (hack::concepts::modern::has_size<T>) {
|
||
// std::cout << "Sized object: " << sized.size() << " elements" << std::endl;
|
||
// } else {
|
||
// std::cout << "Sized object (compile-time size)" << std::endl;
|
||
// }
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::has_key_value_semantics T>
|
||
// void example_has_key_value_semantics(T& container) {
|
||
// if constexpr (hack::concepts::modern::has_mapped_type<T>) {
|
||
// std::cout << "Key-value container, sample access demonstrated" << std::endl;
|
||
// } else {
|
||
// std::cout << "Set-like container" << std::endl;
|
||
// }
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::is_contiguous_container T>
|
||
// void example_is_contiguous_container(const T& container) {
|
||
// std::cout << "Contiguous memory container" << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::can_emplace<std::vector<int>, int> Container>
|
||
// void example_can_emplace(Container& container, int value) {
|
||
// container.emplace_back(value);
|
||
// std::cout << "Emplaced value: " << value << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::can_push_back<std::vector<int>, int> Container>
|
||
// void example_can_push_back(Container& container, int value) {
|
||
// container.push_back(value);
|
||
// std::cout << "Pushed back value: " << value << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::can_push_front<std::list<int>, int> Container>
|
||
// void example_can_push_front(Container& container, int value) {
|
||
// container.push_front(value);
|
||
// std::cout << "Pushed front value: " << value << std::endl;
|
||
// }
|
||
//
|
||
// template<hack::concepts::modern::can_find<std::set<int>, int> Container>
|
||
// void example_can_find(Container& container, int value) {
|
||
// auto it = container.find(value);
|
||
// if (it != container.end()) {
|
||
// std::cout << "Found value: " << value << std::endl;
|
||
// } else {
|
||
// std::cout << "Value not found: " << value << std::endl;
|
||
// }
|
||
// }
|
||
//
|
||
// // Функция для демонстрации not_supported
|
||
// template<typename T>
|
||
// void check_support(const T& value) {
|
||
// if constexpr (modern::concepts::not_supported<T>) {
|
||
// std::cout << "Type is NOT supported by this library" << std::endl;
|
||
// } else {
|
||
// std::cout << "Type is supported" << std::endl;
|
||
// }
|
||
// }
|
||
|
||
auto main(int argc, char *argv[]) -> int
|
||
{
|
||
// Базовые концепты
|
||
std::vector<int> vec = { 1, 2, 3 };
|
||
std::map<int, std::string> map = {{ 1, "one" }, { 2, "two" }};
|
||
std::set<int> set = { 5, 3, 1, 4, 2 };
|
||
std::unordered_map<int, std::string> umap = {{ 1, "uno" }, { 2, "dos" }};
|
||
int a = 10;
|
||
|
||
hack::log()("has_value_type:");
|
||
example_has_value_type(vec);
|
||
// example_has_value_type(a); // выдаст ошибку т.к. у a нет встроенного value_type
|
||
|
||
hack::log()("has_key_type:");
|
||
example_has_key_type(map);
|
||
|
||
hack::log()("has_mapped_type:");
|
||
example_has_mapped_type(map);
|
||
// example_has_mapped_type(set); // выдаст ошибку т.к. у set нет типа mapped_type. Этот тип характерен для контейнеров, которые хранят пары "ключ-значение".
|
||
|
||
hack::log()("has_iterator:");
|
||
example_has_iterator(vec);
|
||
|
||
hack::log()("has_size:");
|
||
example_has_size(vec);
|
||
|
||
hack::log()("has_key_compare:");
|
||
example_has_key_compare(map);
|
||
|
||
hack::log()("has_allocator_type:");
|
||
example_has_allocator_type(map);
|
||
|
||
// // Строки и контейнеры
|
||
// std::string str = "Hello";
|
||
// std::list<double> list = {1.1, 2.2, 3.3};
|
||
// std::deque<char> deque = {'a', 'b', 'c'};
|
||
//
|
||
// std::cout << "6. is_string: ";
|
||
// example_is_string(str);
|
||
//
|
||
// std::cout << "7. is_sequence_container (vector): ";
|
||
// example_is_sequence_container(vec);
|
||
//
|
||
// std::cout << "8. is_sequence_container (list): ";
|
||
// example_is_sequence_container(list);
|
||
//
|
||
// std::cout << "9. is_random_access_container: ";
|
||
// example_is_random_access_container(vec);
|
||
//
|
||
// // Адаптеры и ассоциативные контейнеры
|
||
// std::stack<int> stack;
|
||
// stack.push(1); stack.push(2);
|
||
//
|
||
// std::cout << "10. is_container_adapter: ";
|
||
// example_is_container_adapter(stack);
|
||
//
|
||
// std::cout << "11. is_associative_container: ";
|
||
// example_is_associative_container(set);
|
||
//
|
||
// std::cout << "12. is_unordered_associative_container: ";
|
||
// example_is_unordered_associative_container(umap);
|
||
//
|
||
// // Кортежи и массивы
|
||
// std::tuple<int, std::string, double> tuple = {1, "test", 3.14};
|
||
// int fixed_array[5] = {1, 2, 3, 4, 5};
|
||
// std::array<float, 3> std_array = {1.0f, 2.0f, 3.0f};
|
||
//
|
||
// std::cout << "13. is_tuple_like: ";
|
||
// example_is_tuple_like(tuple);
|
||
//
|
||
// std::cout << "14. is_fixed_array: ";
|
||
// example_is_fixed_array(fixed_array);
|
||
//
|
||
// std::cout << "15. is_std_array: ";
|
||
// example_is_std_array(std_array);
|
||
//
|
||
// // Универсальные концепты
|
||
// std::cout << "16. is_any_container: ";
|
||
// example_is_any_container(vec);
|
||
//
|
||
// std::cout << "17. is_iterable: ";
|
||
// example_is_iterable(vec);
|
||
//
|
||
// std::cout << "18. is_sized: ";
|
||
// example_is_sized(vec);
|
||
//
|
||
// std::cout << "19. has_key_value_semantics: ";
|
||
// example_has_key_value_semantics(map);
|
||
//
|
||
// std::cout << "20. is_contiguous_container: ";
|
||
// example_is_contiguous_container(vec);
|
||
//
|
||
// // Концепты для алгоритмов
|
||
// std::cout << "21. can_emplace: ";
|
||
// example_can_emplace(vec, 42);
|
||
//
|
||
// std::cout << "22. can_push_back: ";
|
||
// example_can_push_back(vec, 99);
|
||
//
|
||
// std::cout << "23. can_push_front: ";
|
||
// example_can_push_front(list, 0);
|
||
//
|
||
// std::cout << "24. can_find: ";
|
||
// example_can_find(set, 3);
|
||
//
|
||
// // Проверка неподдерживаемых типов
|
||
// struct CustomType { int x; };
|
||
// CustomType custom;
|
||
//
|
||
// std::cout << "25. not_supported check (int): ";
|
||
// check_support(42);
|
||
//
|
||
// std::cout << "26. not_supported check (CustomType): ";
|
||
// check_support(custom);
|
||
//
|
||
// std::cout << "\n=== Все примеры выполнены ===" << std::endl;
|
||
|
||
return 0;
|
||
}
|