大哥们,帮忙啊,关于多线程的传递参数问题??100分。
小弟初学多线程,遇到有一问题,请大哥们帮帮小弟。
问题:有一个自定义的 结构(包括int和AnsiString),怎样把它传递给一个线程来处理?
先看小弟的程序实现:
//定义数据类型:
struct param
{
int p1;
AnsiString p2;
};
//定义线程函数:
DWORD WINAPI ThreadFunc(void *p)
{
param para=*((param *)p);
int p1=para.p1;
AnsiString p2=para.p2;
for (int i=0;i<p1;i++)
{
ShowMessage(p2);
}
}
//调用:(button1的单击事件)
void __fastcall TForm1::Button1Click(TObject *Sender)
{
int _case=1;
param para;
para.p1=2;
para.p2="123";
if (_case==0)
{
ThreadFunc((void *)¶);
}
else
{
DWORD dw;
HANDLE hThread=CreateThread(0,0,ThreadFunc,(void *)¶,0,&dw);
}
}
这样就会产生错误,提示如下:
"Project C:\Program Files\Borland\CBuilder6\Projects\Project1.exe faulted with
message: 'access violation at 0x40006880: read of address 0x01fffff9'. Process
Stopped. Use Step or Run to Continue."
不过如果把_case设置为0,就可以顺利执行,也在是说,在同线程里,可以成功调用函数
ThreadFunc,而通过创建新的线程调用就会产生错误,不知道是为什么,请大虾们指点迷津,
小弟不胜感激。
问题点数:100、回复次数:10Top
1 楼jjwwang((空园歌独酌,春日赋闲居))回复于 2006-06-03 06:04:18 得分 20
//---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop
#include "Unit1.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
struct param
{
int p1;
AnsiString p2;
};
//定义线程函数:
DWORD WINAPI ThreadFunc(PVOID p)
{
param para=*((param *)p);
int p1=para.p1;
AnsiString p2 = para.p2;
for (int i=0;i<p1;i++)
{
Form1->Memo1->Lines->Add( "jja" );
}
return 0;
}
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Button1Click(TObject *Sender)
{
int _case=1;
static param para;
para.p1=2;
para.p2="123";
if (_case==0)
{
ThreadFunc((PVOID *)¶);
}
else
{
DWORD dw;
SECURITY_ATTRIBUTES sa;
sa.nLength = sizeof(sa);
sa.bInheritHandle = false;
HANDLE hThread=CreateThread(NULL,0,ThreadFunc,(PVOID)¶,0,&dw);
CloseHandle( hThread );
}
}Top
2 楼jjwwang((空园歌独酌,春日赋闲居))回复于 2006-06-03 06:04:40 得分 10
static param para; 声明为静态的.Top
3 楼jjwwang((空园歌独酌,春日赋闲居))回复于 2006-06-03 06:09:59 得分 0
或者
struct param
{
int p1;
AnsiString p2;
};
param para; //定义为全局的
ButtonClick事件其实也是一个函数, 对于其它线程来说,这个事件中的变量,会随着事件结束而被系统销毁.所以线程访问的时候,报地址访问错误.Top
4 楼xpdavis(咕嘟-不想孤独)回复于 2006-06-03 07:57:50 得分 0
用TThread类Top
5 楼ie521()回复于 2006-06-03 10:10:29 得分 0
大哥,谢谢你,
如果我想把参数传递到进程之后,就释放参数,或者改变参数的值,因为我
还有用新的线程来处理新的数据,比如:
void __fastcall TForm1::Button1Click(TObject *Sender)
{
int _case=1;
param para;
para.p1=2;
para.p2="123";
if (_case==0)
{
ThreadFunc((void *)¶);
}
else
{
DWORD dw;
HANDLE hThread=CreateThread(0,0,ThreadFunc,(void *)¶,0,&dw);
para.p1=3;
para.p2="123";
DWORD dw2;
HANDLE hThread2=CreateThread(0,0,ThreadFunc,(void *)¶,0,&dw2);
}
}Top
6 楼ie521()回复于 2006-06-03 10:17:36 得分 0
能不能就是把参数传递到进程之后,在进程内的para就和外面的无关了,当外面的para
释放(button1 的click 执行完毕)或者外面的para产生变化(para.p1=3),而线程的执行仍然不受影响呢?Top
7 楼ie521()回复于 2006-06-03 10:47:52 得分 0
我说的能不能实现啊?大哥们,帮帮小弟啊,Top
8 楼Persistent8813(固执的,坚持的:山东诸城)回复于 2006-06-03 14:49:18 得分 0
学习Top
9 楼jjwwang((空园歌独酌,春日赋闲居))回复于 2006-06-03 21:15:50 得分 0
能不能就是把参数传递到进程之后,在进程内的para就和外面的无关了,当外面的para
释放(button1 的click 执行完毕)或者外面的para产生变化(para.p1=3),而线程的执行仍然不受影响呢?
//-------------------
那就不要传指针或引用了.按值传递就行了Top
10 楼webmin(webmin)回复于 2006-06-04 16:52:47 得分 70
//每起一个新线程就NEW一个param,在线程中去释放param,也可以等线程执行完后去释放param.
typedef struct
{
int p1;
AnsiString p2;
}param;
DWORD WINAPI ThreadFunc(LPVOID p)
{
param *para=(param *)p;
int p1=para->p1;
AnsiString p2=para->p2;
for (int i=0;i<p1;i++)
{
MessageBoxA(NULL,p2.c_str(),"Test",MB_OK);
}
if(NULL != para)
{
delete para;
para = NULL;
}
return 0;
}
TForm1 *Form1;
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Button1Click(TObject *Sender)
{
int _case=1;
param *para = new param();
para->p1 = 2;
para->p2 = "123";
if (_case==0)
{
ThreadFunc((LPVOID)para);
return;
}
DWORD dw;
HANDLE hThread=CreateThread(NULL,0,ThreadFunc,(LPVOID)para,0,&dw);
//WaitForSingleObject(hThread,INFINITE);
//CloseHandle(hThread);
}Top




