0

DBGridを持っていて、請求書を作成しようとしていますが、計算が実行されない場合があります。どうすればそれを回避できますか?

procedure TOrcamentos.DBGridEh1ColExit(Sender: TObject);
var
  percent: double;
  Unid: double;
  tot: currency;
  vaz: string;
begin
  if Dorcamen_SUB.DataSet.State in [dsEdit, dsInsert] then
    try  
      Dorcamen_SUB.DataSet.Post;
    finally
      vaz := DBGridEh1.Columns[3].Field.text;
      if (vaz<> '') then
        try
          Torcamen_SUB.Edit;
          Unid := (Torcamen_SUB.FieldByName('QT').AsFloat);
          tot := (Torcamen_SUB.FieldByName('Precovenda').AsFloat);
          percent := (Torcamen_SUB.FieldByName('Desconto').AsFloat);
          try
            tot := tot+(tot * percent)/ 100;
          finally
            Torcamen_SUB.FieldByName('Total').AsFloat := unid*tot;
            Torcamen_SUB.Post;
            Orcamentos.TotalExecute(self);
          end;
        except
        end;
    end;
end;
4

2 に答える 2

2

計算を実装するためのより良い方法は、実際には、グリッドがリンクされているTTableコンポーネントに計算を移動することです。Totalフィールドは、実際にはデータベース内のフィールドではなく、他のフィールドの値に基づいて計算されたフィールドである必要があります。テーブルのフィールドエディタを使用してフィールドを追加し、フィールド名Totalを入力し、正しいデータ型を選択してから、フィールドタイプを[計算済み]として選択するだけです。[OK]をクリックして、テーブルのOnCalcFieldイベントに次のようなコードを追加します。

Torcamen_SUB.FieldByName('Total')。AsFloat:= Torcamen_SUB.FieldByName('QT')。AsFloat *(Torcamen_SUB.FieldByName('Precovenda')。AsFloat +(Torcamen_SUB.FieldByName('Precovenda')。AsFloat * Torcamen_SUB.FieldByName ('Desconto')。AsFloat)/ 100);

一般的な経験則では、本当に必要な場合を除いて、計算値をデータベースに保存しないでください。それらを計算フィールドとしてデータセットに追加し、グリッドをデータセットにリンクするのが最善です。次に、すべての計算フィールドがグリッドに表示され、各行には、その行の値に基づいて正しい計算値が表示されます。

于 2011-01-25T03:54:39.473 に答える
1

ビジネスロジック(合計の計算など)とユーザーインタラクションロジック(グリッド列のフォーカスが失われるイベントなど)を組み合わせていると思います。これが、アプリケーションの不安定な動作の原因です。

どこで起こっているのか、どこで起こっていないのか、あなたも知らないようです。

この種の計算を実行するには、フィールドのイベント(たとえば、OnChangeイベント)を使用することを検討してください。

集計機能を備えたデータセット(TClientDataSetなど)を使用している場合は幸運です。TAggregateFieldで必要なものを宣言するだけで、 「手動」で計算することを忘れることができるからです。

あなたの質問ではありませんが...try/finallyの使用方法にも注意してください...たとえば、次のコードでは次のようになります。

try
  tot := tot+(tot * percent)/ 100;
finally
  Torcamen_SUB.FieldByName('Total').AsFloat := unid*tot;
  //other things
end;

何らかの理由でtry句とfinally句の間の行で例外が発生した場合、変数totの値は未定義(この場合は前の割り当ての結果)になるため、Torcamen_SUB.totalフィールドへの割り当てに注意してください。結局のところ、間違っているでしょう。それが本当にあなたが望むものであるかどうかはわかりません。

于 2011-01-24T23:29:31.540 に答える