Delphi 将数据类型ftFloat转换为ftBCD

Delphi 将数据类型ftFloat转换为ftBCD,delphi,casting,bcd,Delphi,Casting,Bcd,如何将字段类型从ftFloat转换为ftBCD 我试过了 for i := 0 to FDataSet.FieldCount - 1 do begin if FDataSet.Fields.Fields[i].DataType = ftFloat then begin FDataSet.Fields.Fields[i].DataType := ftBCD; end; end; 但是我得到了错误 [DCC Error] E2129 Cannot a

如何将字段类型从ftFloat转换为ftBCD

我试过了

for i := 0 to FDataSet.FieldCount - 1 do begin
      if FDataSet.Fields.Fields[i].DataType = ftFloat then begin
           FDataSet.Fields.Fields[i].DataType := ftBCD;
      end;
end;
但是我得到了错误

[DCC Error]  E2129 Cannot assign to a read-only property

是否有一种方法可以将所有数据集字段ftFloat转换为ftBCD?

否!一旦你创建了一个数据域,你就不能改变它!这是因为分配Filedtype不仅仅是更改枚举类型属性。每个字段类型都是一个特定的类: 丁特格菲尔德等

因此,不能更改字段类型,原因与不能将TList转换为字符串相同

很抱歉,你想说什么


Jens Borrisholt

数据类型是为数据类型创建的Tfield的只读属性。 这是使用数据库中TFieldClass的DefaultFieldClasses:array[TFieldType]从Fielddefs完成的。 如果需要更改数据类型,则必须释放该字段并创建另一个适合您需要的字段。 下面显示了如何实现这一点的示例

type
  TMyFieldInfo = Record
    FieldName: String;
    Size: Integer;
    DataType: TFieldType;
    FieldKind: TFieldKind;
  end;

type
  TFA= Array of TMyFieldInfo;

 Procedure GetFields(DS:Tdataset;var FA:TFA);
  var
    I: Integer;
  begin
    SetLength(FA, DS.FieldCount);
    for I := 0 to DS.FieldCount - 1 do
    begin
      FA[I].FieldName := DS.Fields[I].FieldName;
      FA[I].DataType := DS.Fields[I].DataType;
      FA[I].Size := DS.Fields[I].Size;
      FA[I].FieldKind := fkdata;
    end;
  end;

  Procedure SetFields(DS:Tdataset;var FA:TFA);
  var
    I: Integer;
    F:TField;
  begin
    DS.Fields.Clear;
    for I := Low(FA) to High(FA) do
    begin
      F := DefaultFieldClasses[FA[I].DataType].Create(DS);
      With F do
      begin
        FieldName := FA[I].FieldName;
        FieldKind := FA[I].FieldKind;
        Size := FA[I].Size;
        DataSet := DS;
      end;
    end;

  end;


procedure TForm6.Button1Click(Sender: TObject);
var
   L_FA: TFA;
   I:Integer;
begin
    MyDS.Open;  // open to get the Fielddefs.
    GetFields(MyDS,L_FA);
    MyDS.Close;  // close to be able to change the fields
    for I := Low(L_FA) to High(L_FA) do
      begin
         if L_FA[i].DataType = ftFloat then
            L_FA[i].DataType := ftBCD;
      end;
    SetFields(MyDS,L_FA);
    MyDS.Open;
end;
还有一种方法:

首先,需要将表转储到如下文件中

ADOQuery.SaveToFile('C:\1.xml');
然后在其中找到您的字段描述,假设如下:

<s:datatype dt:type='float' dt:maxLength='8' rs:fixedlength='true' rs:maybenull='true'/>
<s:datatype dt:type='number' rs:dbtype='currency' dt:maxLength='25' rs:precision='25' rs:fixedlength='true' rs:maybenull='true'/>
ADOQuery.LoadFromFile('C:\1.xml');

数据类型绑定到字段的类。您必须释放该字段并创建一个TFloatField,然后将其添加到数据集中。执行此操作时,数据集必须关闭。可以看到一个例子,你在使用Firedac吗?如果是,则设置连接的formatoptions.maprules属性。添加带有源ftBCD和目标ftFloat的规则。@副驾驶否,我没有使用Firedac。@bummi ty,然后我将所有ftFloat的数据集创建为ftBCD,我的问题就解决了,ty为我指明了解决方案。把它作为一个答案贴出来,这样我就可以接受了。你是否意识到这样做会失去准确性?TDataSet的类是什么?我有一个rave报告,它需要ftBCD,但是我的数据集中的十进制文件需要传递给rave,它返回ftFloat。因此,我必须以某种方式将它们转换为ftBCD。很好,下次我遇到类似问题时,我将尝试此解决方案。此外,您可能不使用文件,请检查以下问题: