gpt4 book ai didi

sqlite - 如何在 COBOL 中编写 SQLite 回调

转载 作者:IT王子 更新时间:2023-10-29 06:26:21 26 4
gpt4 key购买 nike

我是一名 COBOL 程序员,我最近的项目是将 COBOL 应用程序连接到 SQLite3 数据库。

我一直在关注this guide ,他们的解决方案正是我在 COBOL 应用程序中所需要的。我已经成功创建、连接、插入数据和关闭数据库,但是当我尝试从数据库中选择数据时出现问题。

在教程中,他们使用双指针回调。

static int callback(void *NotUsed, int argc, char **argv, char **azColName){
int i;
for(i=0; i<argc; i++){
printf("%s = %s\n", azColName[i], argv[i] ? argv[i] : "NULL");
}
printf("\n");
return 0;
}

我在 COBOL 中的解决方案如下

   WORKING-STORAGE SECTION.
*----------------------------------------------------------------*

01 sqlite3-db pointer.
01 err_msg pointer.
01 sqlite pointer.
01 res pointer.

01 notused pointer.
01 argc pic 99 comp-5.
01 argv pointer.
01 azColName pointer.
01 Writefunction-Ptr procedure-pointer.

procedure division.
set Writefunction-Ptr to entry "sqlite-callback".

*>Random code.

call "sqlite3_exec" using
by value sqlite3-db
by reference sqlQuery
by value Writefunction-Ptr
by value 0
by reference err_msg
returning rc
end-call

*>Random code.

stop run.

entry "sqlite-callback" using
by value notused
by value argc
by reference argv
by reference azColName.

display argc

goback.
Entry-Termination.

回调有效,因为它称为从数据库返回的行数,整数 argc 包含表包含的列数。

问题是:

COBOL 中的双指针,它们是如何表示的?在我的解决方案中,我声明了一个指针并在指针上使用“通过引用”调用回调。不知道这是否是在 COBOL 中表示双指针的正确方法?

如何显示 azColName 和 argv 的内容,而不仅仅是指针指向的内存地址?

我现在尝试使用 SET ADDRESS OF,但我仍然无法正常工作。一定是我错过了什么。我目前的解决方案如下:

WORKING-STORAGE SECTION.
01 argv pointer.

Linkage Section.
01 link-area pic x.

procedure division using link-area.

*> RANDOM CODE

set address of link-area to argv
call "sqlite3_exec" using
by value sqlite3-db
by reference z"SELECT * FROM Cars"
by value Writefunction-Ptr
by value 0
by reference err_msg
returning rc
end-call

*> RANDOM CODE


entry "sqlite-callback" using
by value notused
by value argc
by reference argv
by reference azColName.

display argc.

if address of link-area not = null
display "Contents of new argv: " link-area
else
display "empty"
end-if

goback.

Entry-Termination.

我得到的结果是 if 语句始终为 false,因此显示字符串“empty”。但是 argc 仍然设置为表中的列数。

工作解决方案:

   WORKING-STORAGE SECTION.

01 argv.
03 firstColumn pointer.
03 secondColumn pointer.
03 thirdColumn pointer.

01 azColName pointer.
01 argc pic 99 comp-5.
01 notused pointer.

01 Writefunction-Ptr procedure-pointer.

*-----------------------------------------------------------------
Linkage Section.

01 Cars_Id pic 9(2).
01 Cars_Name pic X(20).
01 Cars_Price pic 9(10).
/-----------------------------------------------------------------
procedure division.

//code

set Writefunction-Ptr to entry "sqlite-callback".

initialize sqlQuery
move z"SELECT * FROM Cars;" to sqlQuery


call "sqlite3_exec" using
by value sqlite3-db
by reference sqlQuery
by value Writefunction-Ptr
by value 0
by reference err_msg
returning rc
end-call

//code

stop run.



entry "sqlite-callback" using
by value notused
by value argc
by reference argv
by reference azColName.

set address of Cars_Id to firstColumn
set address of Cars_Name to secondColumn
set address of Cars_Price to thirdColumn


display Cars_Id "|" Cars_Name "|" Cars_Price

goback.
Entry-Termination.

最佳答案

我们真的需要知道您使用的编译器。

您的 SET 语句位置错误。 argv 只有在调用 ENTRY 时才有地址。在条目被调用之前,它将是二进制零,或者一些不可预知的垃圾。

如果您将 SET 移到 ENTRY 之后,您应该能够使用 LINK-AREA 的值。 argv 仍然只是一个地址,但是 LINK-AREA(请给它一个更好的名字)将指向那个地址,所以定义它作为 argv 应该被定义,然后 LINK-AREA 可以用于获取argv的实际内容。


当使用BY REFERENCE 时,编译器生成代码来传递带有数据项地址的指针。

PROCEDURE DIVISION USINGENTRY USING 中,该项目也应该是 BY REFERENCE,编译器生成代码以将您的 LINKAGE SECTION 定义映射到传递的地址。

如果您使用 BY CONTENT,这与此类似,但编译器会在您的程序中获取数据的副本,并传递一个引用该数据的指针。关于仍然定义为 BY REFERENCE 的 PROCEDURE DIVISION 或 ENTRY 的 USING。

使用 BY VALUE 时,编译器“传递”实际值,尽管存在限制,无论是标准中指定的值还是实际编译器对标准的扩展。 PROCEDURE DIVISION 或 ENTRY 的 USING 也应指定 BY VALUE。

在所有 USING 上,BY REFERENCE/CONTENT/VALUE 被传播,如果所有内容都相同并且您想要 BY REFERENCE,则根本不需要指定 BY,这是默认值。

如果您“传递”POINTER(USAGE POINTER),那么您可以使用SET ADDRESS OF 访问指向的数据。 SET ADDRESS OF 项必须在 LINKAGE SECTION 中。

您还可以使用带有 SET ADDRESS OF 的隐式指针。 SET ADDRESS OF a TO ADDRESS OF b 会将 LINKAGE SECTION 中映射的地址更改为 b 的地址,b 是在程序的 DATA DIVISION 某处定义的项目( 之外的任何 SECTION文件部分).

如果您想查看 POINTER 指向的数据,请定义一个具有正确大小和类型的项目,并使用 SET ADDRESS OF item TO pointer-name。

指针当然可以指向一个简单的数据项或一组数据项(结构)。

LINKAGE SECTION 中的所有项目在被引用之前必须有一个地址。 USING 上的那些由编译器赋予可寻址性(并且编译器假定传递了正确数量的地址/项目)。所有其他 LINKAGE SECTION 项必须具有通过 SET ADDRESS OF 或通过在使用 CALL 时传递 ADDRESS OF 并让 CALLed 程序设置地址来建立的可寻址性。

关于sqlite - 如何在 COBOL 中编写 SQLite 回调,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34356757/

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