Моя C ++ DLL возвращает данные, смешанные из 2 последовательных вызовов - PullRequest
1 голос
/ 27 февраля 2012

Я написал C ++ DLL с использованием VS 2010, который используется для переноса некоторой программы, которая выполняет логические операции над полигонами. Ее структура выглядит следующим образом: Есть главный заголовок и .cpp, чьи методы представлены метками:

  __declspec(dllexport) 

Затем внутри одного из этих методов я выполняю вызов одного из методов моей многоугольной программы, которая содержится в другом классе c ++, который является частью библиотеки. Я должен отметить, что в дополнение к вызову этого метода я также Создайте (в главном файле dll .cpp) переменные, которые определены в этой программе для полигонов. Эти переменные имеют типы, необходимые для передачи и получения числовых данных из программы для полигонов. Теперь, что не так. Когда я запускаю приложение, которое использует эту dll, я делаю два одинаковых вызова одного и того же метода библиотеки - тот, который я объяснил выше, который вызывает функцию программы polygon. Когда я выполняю эти вызовы, я передаю некоторые числовые данные в метод и ожидают получения новых данных, основанных на некоторых вычислениях в программе полигонов. Первый вызов возвращает правильные данные, но второй возвращает вид смешивания данных из первого вызова и вторых входных данных. Я не эксперт по DLL, но я взглянул на эту тему:

Как использовать extern для обмена переменными между исходными файлами?

И мне интересно, может ли это быть источником проблемы? Как я уже упоминал, я использую некоторые переменные, которые являются частью класса вычисления многоугольника, и я создаю их экземпляры в основном .cpp библиотеки DLL. Две из этих переменных принимают входные данные от пользователя и передают их в метод, который вычисляет результат, а третья переменная заполняется результатом, возвращаемым этой функцией. Буду очень признателен за любую помощь, так как в данный момент я действительно застрял в ней.

РЕДАКТИРОВАТЬ: переменные, которые я использую из исходного класса полигона, определены в его заголовке следующим образом:

 typedef std::vector< IntPoint > Polygon;
 typedef std::vector< Polygon > Polygons;

Программа тестирования DLL

#include "stdafx.h"
#include "Clipper_lib.h"

int _tmain(int argc, _TCHAR* argv[])
{
int subj[]={100,100,200,100,200,200,100,200};
int clip[]={100,100,200,100,200,200,100,200};
vector<vector<int>> solution;
vector<vector<int>> solution1;
Execute(subj,clip,solution);

Execute(subj,clip,solution1);


return 0;
}

Заголовок DLL:

 #include "clipper.hpp"  /// this is the working C++ class of polygons operations
 #include <vector>
 using namespace ClipperLib;
 using namespace std;
 extern Polygon subj;
 extern Polygon clip;
 extern Polygons solution;

 extern "C"
 {
__declspec(dllexport) void Execute(int subj[],int clip[],vector<vector<int>> &solution);

 }

DLL .cpp

// Clipper_lib.cpp : Defines the exported functions for the DLL application.
//
#include "Clipper_lib.h"

Clipper clipper;

void Execute(int subj[],int clip[],vector<vector<int>> &solution){

Polygon *subjP=new Polygon();
Polygon *clipP=new Polygon();
Polygons *solutionP=new Polygons();



 for(int i=0; i<8;i+=2){

     subjP->push_back(IntPoint(subj[i],subj[i+1]));

 }


 for(int b=0;b<8;b+=2){

     clipP->push_back(IntPoint(clip[b],clip[b+1]));
 }
 clipper.Clear();
 clipper.AddPolygon(*subjP,ptSubject);
 clipper.AddPolygon(*clipP,ptClip);
 clipper.Execute(ctIntersection,*solutionP);
for( vector<Polygon>::size_type d=0;d!=solutionP->size();++d){
    vector<int> poly;
    solution.push_back(poly);

    for(vector<IntPoint>::size_type k=0;k!=solutionP[d].size();++k){

        for(vector<IntPoint>::size_type s=0;s!=solutionP[d][k].size();++s){

            int numX=(int)solutionP[d][k][s].X;
            int numY=(int)solutionP[d][k][s].Y;
            solution[d].push_back(numX);
                solution[d].push_back(numY);
        }



    }



}
delete solutionP;
delete subjP;
delete clipP;

}

Ответы [ 3 ]

1 голос
/ 28 февраля 2012

Хорошо. Настроил это. Так как оболочкой этого источника был API на основе C, мне пришлось включить все методы C ++ в DLL с помощью extern "C". Таким образом, он работает отлично. В любом случае, спасибо за все комментарии.

0 голосов
/ 27 февраля 2012

Разве вы не можете отладить вызов библиотеки?

Например. пройти через это в отладчике и попытаться увидеть, где устанавливаются недопустимые значения. Многие IDE позволяют устанавливать точки останова, которые срабатывают при изменении данных в определенном месте памяти. Вы можете установить точку останова на значение, которое, как вы знаете, будет неправильно установлено при втором вызове, и оно покажет вам, что его меняет.

0 голосов
/ 27 февраля 2012

Более простая вещь: после того, как вы использовали данные из Полигоны , вызовите clear () для нее. clear () - это быстрый метод, который сохраняет выделенную память (на случай, если вы опасаетесь за эффективность), но помечает содержимое как недоступное. Таким образом, вы можете без проблем заполнить Полигоны новыми данными. Внутренние векторы, то есть объекты типа Polygon , будут очищаться по запросу, вы можете игнорировать их.

...