Итак, у меня есть этот проект, где я должен воссоздать самые основные функции MySQL, работая над базой данных Songs (которые представлены в классе).
Я создал еще один класс, который является моим интерфейсом (пользовательский интерфейс). Я использую его для получения команд, распознавания параметров и так далее. Я хочу создать функцию более высокого порядка, которая принимает несколько параметров. Некоторые из них будут примитивными типами данных, но также будут две функции в качестве параметров.
Теперь одна из функций происходит из того же класса (Interface), но другая функция происходит из класса Songs. Проблема в том, что я не могу понять, как ссылаться на функцию в этом классе?
Я думал о том, чтобы сделать класс статичным, потому что вы все равно можете создать только одну базу данных типа Songs. Скорее всего, это дало бы мне возможность использовать справочник Songs ::, но я не уверен, что это решит мою проблему.
Помимо решения, я также прошу более подробное объяснение функций высшего порядка в C ++, я не могу найти хороший ресурс. И все ресурсы, которые я обнаружил, ничего не говорят о функциях высшего порядка, которые получают параметры функций из других классов.
class Song
{
public:
string getName() const;
string getSinger() const;
unsigned int getLength();
unsigned short getYear() const;
private:
char singer[51];
char name[51];
unsigned int length;
unsigned short year;
};
А затем в интерфейсе:
bool isEqual(string, string);
template<typename T>
bool isSmaller(T firstElement, T secondElement);
template<typename T>
bool isGreater(T firstElement, T secondElement);
Я хочу создать функцию более высокого порядка, которая проверяет значение функции компаратора. Однако одно из значений, которое должен принимать компаратор, должно исходить от объекта Songs. Другими словами, я должен также передать одного из 4 добытчиков, в зависимости от ситуации.
Вы хотите использовать указатели на функции-члены. А вот простой пример универсальной функции высшего порядка:
template <typename T, typename Func>
void Call(T* obj, Func T::* memFuncPtr)
{
(obj->*memFuncPtr)();
}
Call
принимает общий указатель объекта и указатель на функцию-член класса этого объекта и просто вызывает эту функцию. Например,
class A
{
public:
void foo()
{
cout<<"A::foo() called\n";
}
void bar()
{
cout<<"A::bar() called\n";
}
};
int main()
{
A a;
Call(&a, &A::foo);
return 0;
}
В дополнение к указателям на функции-члены Boost.FunctionTypes библиотека дает вам дескриптор функции подписи. Эти методы должны быть хорошей отправной точкой.
Обратите внимание: если вы не хотите использовать шаблоны, вы можете написать неуниверсальное определение, указав тип объекта и сигнатуру функции-члена.
void CallA(A* obj, void (A::*)() memFuncPtrOfA)
{
(obj->*memFuncPtr)();
}
Поскольку оба A::foo
а также A::bar
удовлетворить подпись функции в CallA
Второй аргумент, вы можете назвать их обоих:
A a;
CallA(&a, &A::foo);
CallA(&a, &A::bar);