Передать функцию в библиотеку динамических ссылок - PullRequest
1 голос
/ 09 ноября 2019

Мне нужно передать функцию внутри проекта библиотеки динамических ссылок. В этом проекте у меня есть две функции:

HRESULT solve_serial(solver::TSolver_Setup &setup, solver::TSolver_Progress &progress) {
  start(setup.max_generations, setup.population_size, setup.problem_size, setup.lower_bound, setup.upper_bound);
}

void start(size_t problem_size, size_t max_generation, size_t population_size, const double* lower_bound, const double* upper_bound)
{
    while (t <= MaxGeneration)
    {
        for (i = 0; i < n; i++)
        {
            // ---------- HERE I NEED TO USE PASSED FUNCTION -------------
            f[i] = function(ffa[i]);  // obtain fitness of solution
            I[i] = f[i];                        // initialize attractiveness
        }
    }
}

solve-serial вызывается из внешней программы, и он получит &setup с функцией, которую мне нужно передать внутри функции start, где я буду ее использовать.

Вот так solver::TSolver_Setup выглядит следующим образом:

using TObjective_Function = double(IfaceCalling*)(const void *data, const double *solution);

struct TSolver_Setup {
    const TObjective_Function objective;
};

Как мне пройти функцию? Я не могу изменить solver::TSolver_Setup, но я могу изменить start (или переменные внутри того же файла).

Ответы [ 2 ]

0 голосов
/ 09 ноября 2019

Если я хорошо понимаю, проблема в том, как передать функции (или, точнее, указатели на функции) в качестве аргумента и как их использовать.

Я понимаю, что setup содержит указатель на функцию с именем objective:

struct TSolver_Setup {
    const TObjective_Function objective;
    //....  (apparently a lot of other stuff you didn't talk about)
};

Я также понимаю, что вам нужно вызвать эту функцию в start (), встрока, в которую вы помещаете комментарий заполнителя. Однако неясно, где следует хранить значение, а не какие аргументы следует использовать, поэтому я буду использовать некоторые предположения и заполнители. Если бы у вас был доступ к setup, вы могли бы просто сделать:

ffa[i] = setup.objective (&whatdata, &what solution); 

Но так как вы не передаете setup в start(), вам придется по крайней мере передать функцию для запускаиспользуя дополнительный параметр f:

void start(size_t problem_size, size_t max_generation, size_t population_size, const double* lower_bound, const double* upper_bound, TObjective_Function f)
{
    ...
            ffa[i] = f (&whatdata, &what solution);// <---------- HERE IT IS ----------
    ...
}

и передать параметр, вам просто нужно передать objective:

HRESULT solve_serial(solver::TSolver_Setup &setup, solver::TSolver_Progress &progress) {
  start(setup.max_generations, setup.population_size, setup.problem_size, setup.lower_bound, setup.upper_bound, setup.objective);
  return 0;  // you must return something !
}

Если это не отвечает на ваш вопрос, дайте мне знать, чтобы я скорректировал свой ответ. Но в этом случае вам необходимо сначала уточнить, в чем конкретно заключается ваша проблема, что вы пытались, и указать недостающие элементы, которые позволили бы нам повторить проблему.

0 голосов
/ 09 ноября 2019

изменить функцию запуска, чтобы включить ссылку на установку

void start(olver::TSolver_Setup &setup,.....)

запуск вызова:

start(setup,....

функция вызова:

setup.objective(data,solution)
...