Visual Studio — MSVS2010 Консольный код C ++, портированный на MSVS2010 Графический интерфейс C ++ не работает. Зачем?

Я только что закончил проверку концепции или, как мне показалось, подачи Microsoft Visual Studio 2010 некоторого кода C ++ в качестве консольной программы. Скомпилированный код C ++ приведен ниже:

#include "stdafx.h"#include <stdio.h>
#include <Windows.h>
#include <stdlib.h>
#include <sndfile.h>//The following libraries are related to parsing the text files
#include <iostream> //Open the file
#include <fstream> //Reading to and from files//The following libraries are for conducting the DTW analysis
#include "dtw.h"
using namespace std;

int _tmain(int argc, _TCHAR* argv[])
{
printf("This is a test\n");//This will be the length of the buffer used to hold samples while the program processes them.//A SNDFILE is like FILE in a standard C library. Consequently, the sf_open_read and sf_open_write functions will return an
//SNDFILE* pointer when they successfully open the specified file.
SNDFILE* sf = NULL;

/*SF_INFO will obtain information of the file we wish to load into our program. */
SF_INFO info;

/*The following is descriptive information to obtain from wave files. These are declarations*/
int num_channels;
double num, num_items;S
double *buf;
int f, sr, c;
int i,j;
FILE *out;/*This is where the program will open the WAV file */
info.format = 0;
sf = sf_open("C:\\Users\\GeekyOmega\\Desktop\\gameon.wav", SFM_READ, &info);
if(sf == NULL)
{
printf("Failed to open the file.\n");
getchar();
exit(-1);
}

/*Print some file information */
f = info.frames;
sr = info.samplerate;
c = info.channels;

/*Print information related to file*/
printf("frames = %d\n",f);
printf("sample rate = %d\n",sr);
printf("channels = %d\n",c);

/*Calculate and print the number of items*/
num_items = f*c;
printf("Read %lf items\n", num_items);

/*Allocate space for the data to be read*/
buf = (double *) malloc(num_items*sizeof(double));
num = sf_read_double(sf,buf,num_items);
sf_close(sf);

/*print the information*/
printf("Read %lf items\n", num);/*Write the data to the filedata.out*/
out = fopen("filedata.txt", "w");
for(i = 0; i < num; i+=c)
{
for(j = 0; j < c; ++j)
{
fprintf(out, "%lf ", buf[i +j]);
}
fprintf(out,"\n");
}
fclose(out);

}

Итак, далее, и это очень важно, я хочу, чтобы это работало с графическим интерфейсом. То есть я загружаю любой файл, который мне нужен, и он преобразует этот файл в текстовый формат. Я предоставляю этот код ниже:

#pragma once
//Libraries required for libsndfile
#include <sndfile.h>
#include <stdlib.h>
#include <stdio.h>
#include <iostream>
#include <fstream>namespace WaveGui {

using namespace System;
using namespace System::ComponentModel;
using namespace System::Collections;
using namespace System::Windows::Forms;
using namespace System::Data;
using namespace System::Drawing;

using namespace System::Runtime::InteropServices;using namespace std;

/// <summary>
/// Summary for Form1
/// </summary>

Я отредактировал это для удобства чтения. Это была стандартная форма MSVS2010. Я только добавил кнопку и открыть диалоговое окно файла.

    private: System::Void button1_Click(System::Object^  sender, System::EventArgs^  e)
{

if(openFileDialog1->ShowDialog() == System::Windows::Forms::DialogResult::OK)
{
//Note: Ask Gustafson how we might free the memory for this strign
//  http://support.microsoft.com/?id=311259

char* str2 = (char*)(void*)Marshal::StringToHGlobalAnsi(openFileDialog1->FileName);
SNDFILE* sf = NULL;
SF_INFO info;

/*The following is descriptive information to obtain from wave files. These are declarations*/
int num_channels;
double num, num_items;
double *buf;
int f, sr, c;
int i,j;
FILE *out;/*This is where the program will open the WAV file */
info.format = 0;
sf = sf_open(str2, SFM_READ, &info);
if(sf == NULL)
{
exit(-1);
}

/*Print some file information */
f = info.frames;
sr = info.samplerate;
c = info.channels;

/*Calculate and print the number of items*/
num_items = f*c;

/*Allocate space for the data to be read*/
buf = (double *) malloc(num_items*sizeof(double));
num = sf_read_double(sf,buf,num_items);
sf_close(sf);

/*Write the data to the filedata.out*/
out = fopen("filedata.txt", "w");
for(i = 0; i < num; i+=c)
{
for(j = 0; j < c; ++j)
{
fprintf(out, "%lf ", buf[i +j]);
}
fprintf(out,"\n");
}
fclose(out);}}
};
}

В коде для кнопки я преобразовываю системную строку в обычную строку, а затем пытаюсь использовать приведенный выше код C ++ для преобразования моего волнового файла в текстовую информацию. Я знаю, что код преобразования работает, и я знаю, что код кнопки работает, поскольку я тестировал их отдельно. Однако моя библиотека sndfile.h действительно умирает, когда я пытаюсь использовать ее сейчас.

Ошибка, которую я получаю при добавлении библиотек stdio.h, Windows.H, stdlib.h, iostream, fstream, выглядит следующим образом:

1>WaveGui.obj : error LNK2031: unable to generate p/invoke for "extern "C" int __clrcall sf_close(struct SNDFILE_tag *)" (?sf_close@@$$J0YMHPAUSNDFILE_tag@@@Z); calling convention missing in metadata
1>WaveGui.obj : error LNK2031: unable to generate p/invoke for "extern "C" __int64 __clrcall sf_read_double(struct SNDFILE_tag *,double *,__int64)" (?sf_read_double@@$$J0YM_JPAUSNDFILE_tag@@PAN_J@Z); calling convention missing in metadata
1>WaveGui.obj : error LNK2031: unable to generate p/invoke for "extern "C" struct SNDFILE_tag * __clrcall sf_open(char const *,int,struct SF_INFO *)" (?sf_open@@$$J0YMPAUSNDFILE_tag@@PBDHPAUSF_INFO@@@Z); calling convention missing in metadata
1>WaveGui.obj : warning LNK4248: unresolved typeref token (01000027) for 'SNDFILE_tag'; image may not run
1>WaveGui.obj : error LNK2028: unresolved token (0A000022) "extern "C" int __clrcall sf_close(struct SNDFILE_tag *)" (?sf_close@@$$J0YMHPAUSNDFILE_tag@@@Z) referenced in function "private: void __clrcall WaveGui::Form1::button1_Click(class System::Object ^,class System::EventArgs ^)" (?button1_Click@Form1@WaveGui@@$$FA$AAMXP$AAVObject@System@@P$AAVEventArgs@4@@Z)
1>WaveGui.obj : error LNK2028: unresolved token (0A000023) "extern "C" __int64 __clrcall sf_read_double(struct SNDFILE_tag *,double *,__int64)" (?sf_read_double@@$$J0YM_JPAUSNDFILE_tag@@PAN_J@Z) referenced in function "private: void __clrcall WaveGui::Form1::button1_Click(class System::Object ^,class System::EventArgs ^)" (?button1_Click@Form1@WaveGui@@$$FA$AAMXP$AAVObject@System@@P$AAVEventArgs@4@@Z)
1>WaveGui.obj : error LNK2028: unresolved token (0A000025) "extern "C" struct SNDFILE_tag * __clrcall sf_open(char const *,int,struct SF_INFO *)" (?sf_open@@$$J0YMPAUSNDFILE_tag@@PBDHPAUSF_INFO@@@Z) referenced in function "private: void __clrcall WaveGui::Form1::button1_Click(class System::Object ^,class System::EventArgs ^)" (?button1_Click@Form1@WaveGui@@$$FA$AAMXP$AAVObject@System@@P$AAVEventArgs@4@@Z)
1>WaveGui.obj : error LNK2019: unresolved external symbol "extern "C" int __clrcall sf_close(struct SNDFILE_tag *)" (?sf_close@@$$J0YMHPAUSNDFILE_tag@@@Z) referenced in function "private: void __clrcall WaveGui::Form1::button1_Click(class System::Object ^,class System::EventArgs ^)" (?button1_Click@Form1@WaveGui@@$$FA$AAMXP$AAVObject@System@@P$AAVEventArgs@4@@Z)
1>WaveGui.obj : error LNK2019: unresolved external symbol "extern "C" __int64 __clrcall sf_read_double(struct SNDFILE_tag *,double *,__int64)" (?sf_read_double@@$$J0YM_JPAUSNDFILE_tag@@PAN_J@Z) referenced in function "private: void __clrcall WaveGui::Form1::button1_Click(class System::Object ^,class System::EventArgs ^)" (?button1_Click@Form1@WaveGui@@$$FA$AAMXP$AAVObject@System@@P$AAVEventArgs@4@@Z)
1>WaveGui.obj : error LNK2019: unresolved external symbol "extern "C" struct SNDFILE_tag * __clrcall sf_open(char const *,int,struct SF_INFO *)" (?sf_open@@$$J0YMPAUSNDFILE_tag@@PBDHPAUSF_INFO@@@Z) referenced in function "private: void __clrcall WaveGui::Form1::button1_Click(class System::Object ^,class System::EventArgs ^)" (?button1_Click@Form1@WaveGui@@$$FA$AAMXP$AAVObject@System@@P$AAVEventArgs@4@@Z)
1>c:\users\geekyomega\documents\visual studio 2010\Projects\WaveGui\Debug\WaveGui.exe : fatal error LNK1120: 6 unresolved externals

Насколько я могу судить, я правильно установил библиотеку. В конце концов, это прекрасно работает с этими библиотеками в консольной ситуации. Однако, когда я пытаюсь использовать точно такой же код и библиотеки с моей формой графического интерфейса, кажется, что библиотеки не очень хорошо играют друг с другом, и в результате я не могу правильно прочитать мой файл .h и структуры доступа, такие как SNDFILE. ,

Может кто-нибудь, пожалуйста, дайте мне знать, что идет не так? Я потратил на это часы и надеюсь, что мне не придется пересматривать библиотеку libsndfile. Я действительно хочу заставить его работать с MSVS2010, с графическим интерфейсом, и, насколько я могу судить, нет причин, по которым это не должно работать. Но вы знаете, что они говорят, компьютеры не лгут.

Как всегда, спасибо за помощь пациента.
GeekyOmega

0

Решение

Итак, ваше консольное приложение является собственным кодом, но ваше приложение с графическим интерфейсом управляется C ++. Было ли это преднамеренным, или вы намеревались, чтобы ваше приложение с графическим интерфейсом тоже было нативным (Win32) кодом?

Я думаю, вам повезет больше, если вы будете использовать 100% нативный код или, возможно, создадите DLL для инкапсуляции вашего нативного кода и вызовите ее через P / Invoke из вашего .NET GUI. Вот пример использования P / Invoke:

http://manski.net/2012/05/29/pinvoke-tutorial-basics-part-1/

4

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]