gpt4 book ai didi

c - 如何在单独的线程中传递 blt vector

转载 作者:行者123 更新时间:2023-11-30 17:32:15 25 4
gpt4 key购买 nike

我有一个对数据库的函数调用,我正在使用 C 和 tcl/tk,因此该函数的 tcl 调用在 C 中执行,但是当发生这种情况时,tcl 中的系统在处理查询时挂起调用以及它填充 vector 的时间,我希望 tcl 应用程序继续工作并将此进程放在单独的线程中。这就是我现在正在尝试的。

处理数据库调用并填充 vector 的 C 函数:

static int getEpochPrototype(ClientData cdata, Tcl_Interp *interp, int objc, Tcl_Obj *const objv[]){
Tcl_Obj *result;
char sampleid[15];
char tclxVec[15];
char tclyVec[15];
int length;
int numResults;
int i;
Blt_Vector *xCVec, *yCVec;

if (objc != 4) {
Tcl_WrongNumArgs(interp, 3, objv, "number of argument error");
return TCL_ERROR;
}

strcpy(sampleid,Tcl_GetStringFromObj(objv[1], &length));
strcpy(tclxVec,Tcl_GetStringFromObj(objv[2], &length));
strcpy(tclyVec,Tcl_GetStringFromObj(objv[3], &length));

if (Blt_VectorExists(interp, tclxVec) != TCL_OK || Blt_VectorExists(interp, tclyVec) != TCL_OK) {
if ((Blt_GetVector(interp, tclxVec, &xCVec) != TCL_OK) || (Blt_GetVector(interp, tclyVec, &yCVec) != TCL_OK)) {
return TCL_ERROR;
}
} else {
printf("Vector not found \n");
return TCL_ERROR;
}

char command[256];
PQclear(res);

strcpy(command, "select extract ('epoch' from \"Timestamp\"), \"BioAccumulated\" from \"Results\" where \"SampleID\" = '");
strcat(command, sampleid);
strcat(command, "' order by \"Timestamp\" asc");
res = PQexec(conn,command);
numResults = PQntuples(res);
double x[numResults], y[numResults];

for (i = 0; i < numResults; i++)
{
x[i] = strtod(PQgetvalue(res,i,0), NULL);
y[i] = strtod(PQgetvalue(res,i,1), NULL);

}

/* Put the data into BLT vectors */
if ((Blt_ResetVector(xCVec, x, numResults, numResults, TCL_VOLATILE) != TCL_OK) || (Blt_ResetVector(yCVec, y, numResults, numResults, TCL_VOLATILE) != TCL_OK)) {
return TCL_ERROR;
}


return TCL_OK;
}

TCL 函数尝试将 blt vector 发送到 c 线程:

blt::vector create xVec
blt::vector create yVec

tsv::set graph xtemp_shared xVec
tsv::set graph yBio_shared yVec

thread::create {
load ./samples.so
connectDB2

#puts "[tsv::get details sampleid_shared]"
getEpochPrototype [tsv::get details sampleid_shared] [tsv::get graph xtemp_shared] [tsv::get graph yBio_shared]
}

当我尝试这个时,我得到“找不到 vector ”,这是当找不到 vector 或出现错误时我放置的打印语句,是否有其他方法可以做到这一点,或者我错过了什么?

最佳答案

Tcl的threading model要求您从创建 Tcl 解释器的线程访问该解释器的任何特定实例。 (Tcl 的实现广泛使用特定于线程的数据。)您可以从另一个线程填充这些 C 数组 — 通常的 C 并行规则 — 然后使用 Tcl_ThreadQueueEvent告诉另一个线程你有事情要做;你发送的消息实际上是代码+数据。

struct DoneReadingIntoArraysEvent {
Tcl_Event eventHeader;
Tcl_Interp *interp;
double *x, *y;
int length;
}

struct DoneReadingIntoArraysEvent callback;
callback.eventHeader.proc = &MyCallbackFunc;
callback.interp = theInterpHandleInTheOtherThread;
callback.x = x;
callback.y = y;
callback.length = numberOfValuesInArray;
Tcl_ThreadQueueEvent(mainThreadId, &callback.eventHeader, TCL_QUEUE_TAIL);

现在,在MyCallbackFunc中,您将Tcl_Event*参数强制转换回struct DoneReadingIntoArraysEvent(安全;它是第一个成员!)并检索您需要告诉解释器(以及相关解释器)的值。

为了将值实际输入 Tcl,我强烈考虑使用包含一大堆双 Tcl_Obj 的列表 Tcl_Obj。这是 BLT 首次创建时不可用的机制,它的性能可能比您预期的要好。或者,如果值的数量很大,您只需要传递它们和/或存储它们,请发送一大块二进制文件(如果需要,二进制扫描命令将能够挑选出位) .

相关 API 为 Tcl_NewListObjTcl_NewDoubleObjTcl_NewByteArrayObj

关于c - 如何在单独的线程中传递 blt vector ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24292926/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com