sql - 我在delphi中不断收到“标准表达式中的数据类型不匹配”错误
问题描述
每当此代码运行时,我都会收到上述错误。该代码应该将记录插入表中,然后从另一个表中删除记录。
for I := iMax - K to iMax do
begin
Inc(a);
with dmMenu.qryMcDonalds do
begin
SQL.Text :=
'SELECT ID, ItemID, ItemPrice, ItemCategory FROM tblCheckout WHERE ID = ' + IntToStr(I);
Open;
sItemID := Fields[1].AsString;
rItemPrice := Fields[2].AsFloat;
sItemCategory := Fields[3].AsString;
ShowMessage(IntToStr(I));
// I get the error here
SQL.Text :=
'INSERT INTO tblOrderItems (OrderItemID, OrderID, ItemID, ItemCategory, ItemPrice) VALUES ("' + sOrderID + '_' + IntToStr(a) + '"' + ', "' + sOrderID + '", "' + sItemID + '", "' + sItemCategory + '", "' + FloatToStrF(rItemPrice, ffCurrency, 10, 2) + '")';
ExecSQL;
SQL.Text := 'DELETE FROM tblCheckout WHERE ID = ' + IntToStr(I);
ExecSQL;
end; // with SQL
end; // for I
编辑:我认为问题出在“插入”部分。除最后一列外,所有列都是短文本,ItemPrice 是一种货币。我也在使用 Access
解决方案
请在主窗体上仅使用以下项目开始一个新项目:
- 一个 TAdoConnection 配置为连接到您的数据库;
- 配置为使用 TAdoConnection 的 TAdoQuery
- 一个 TDataSource 和 TDBGrid 配置为显示 TAdoQuery 的内容。
然后,将以下代码添加到表单中
const
sSelect = 'select * from tblOrderItems';
sInsert = 'insert into tblOrderItems(OrderItemID, OrderID, ItemID, ItemCategory, ItemPrice) '#13#10
+ 'values(:OrderItemID, :OrderID, :ItemID, :ItemCategory, :ItemPrice)';
sOrderItemID = '0999';
sOrderID = '1999';
sItemID = '2999';
sItemCategory = 'Bolt';
fItemPrice = 5.99;
procedure TForm2.FormCreate(Sender: TObject);
begin
AdoQuery1.SQL.Text := sInsert;
AdoQuery1.Prepared := True;
AdoQuery1.Parameters.ParamByName('OrderItemID').Value:= sOrderItemID;
AdoQuery1.Parameters.ParamByName('OrderID').Value := sOrderID;
AdoQuery1.Parameters.ParamByName('ItemID').Value := sItemID;
AdoQuery1.Parameters.ParamByName('ItemCategory').Value := sItemCategory;
AdoQuery1.Parameters.ParamByName('ItemPrice').Value := fItemPrice;
AdoQuery1.ExecSQL;
AdoQuery1.SQL.Text := sSelect;
AdoQuery1.Open;
end;
在编译和运行程序之前,检查并更改常量的值,使它们不会与表中已有的任何行发生冲突。
常量 sInsert 定义了一个所谓的“参数化 SQL 语句” 在Values
列表中,项目 :OrderItemID、:OrderID 等是占位符,AdoQuery 将其转换为参数,您可以在运行时提供其值,如块后 AdoQuery1.Parameters.ParamByName(...
您应该始终以这种方式构造 SQL 语句,而不是像代码尝试那样连接字符串。它更不容易出错,因为如果您使用 DIY 代码很容易陷入语法混乱,而且它还确保您的查询不容易受到Sql-Injection 攻击,如果您给用户机会编辑 SQL。
如果您使用的是 FireDAC FDQuery,它具有Params
(FD 数据类型)而不是参数,但它们的工作方式几乎相同 - 请参阅在线帮助。
将来,请更加小心,以确保您包含重要的详细信息,尤其是发生错误的确切行 - 您可以通过使用调试器单步执行代码来检查 - 以及确切的 db-access您正在使用的组件。还要尝试正确获取详细信息,例如列是“短文本”类型还是自动编号。
对于需要调试的问题,比如这个问题,你还应该提供一个完整的、最小的、可重现的示例,而不仅仅是一段代码。很多时候,您会在准备 mre 时意识到问题所在,因此它对您和我们都有帮助。
推荐阅读
- c# - 在 VS2019 中使用 iFort 从 C# 调用 Fortran
- javascript - 窗口添加事件侦听器负载不适用于 text/babel
- python - python中对的最佳匹配
- google-sheets - 返回倒数第二个匹配的 ArrayFormula
- c# - OpenXML 用实际图像替换图像占位符替换所有占位符
- android - 视图类型绑定找不到生成的模块 - Android Kotlin
- python - 从父子列表中有效地构造所有后代的列表 - Python/Pandas
- r - 在列中,我想 gsub 字符串值的每一行并删除与我创建的值列表匹配的任何值
- c - C 大数乘法
- bash - 带有 cat 和管道的 Bash 读取命令