1

FoxPro から SQL Server にコードを少し変換しようとしていますが、非常に奇妙な動作に直面しています。

FoxPro のアプリケーションで書かれたこのコード:

lcZnak1 = "HM,P6";

SELECT Zakslozkap.datum,ABS(Zakslozkap.hodnota) hodnota, ABS(Zakslozkap.koruny)
koruny, Zakslozka.sekce;
FROM Zakslozkap, Zakslozka; 
WHERE (Zakslozkap.SW $ lcZnak1) AND;
BETWEEN(Zakslozkap.datum,Thisform.cDatOd,Thisform.cDatDo) AND ;
Zakslozkap.ide_slozka = Zakslozka.ide_slozka AND ;
Zakslozka.ide_zak = "6065" ;
INTO CURSOR QueryNakladMZD

SUM (koruny) FOR  sekce $ ('REZIE4') TO lnostat
SUM (koruny) FOR  sekce $ ('REZIE3') TO lnRezie
SUM (koruny) FOR  sekce $ ('SEKTOR') TO lnSekce
SUM (koruny) TO lnPodil

lnPodil= lnPodil - lnostat - lnRezie - lnSekce

lnPodil = 1 721 761,07 の結果を生成します。

SQL で書かれた私のコード:

declare @lnOstat decimal(18,5) = 0
declare @lnRezie decimal(18,5) = 0
declare @lnSekce decimal(18,5) = 0
declare @lnPodil decimal(18,5) = 0  

select p.datum, abs(p.hodnota) as 'hodnota', abs(p.koruny) as 'koruny', z.sekce into #tmp
from [DOCHAZKA]...[zakslozkap] p, [DOCHAZKA]...[zakslozka] z
where (p.SW = 'HM' or p.SW = 'P6')
      and p.datum between @datestart and @dateend
      and p.ide_slozka = z.ide_slozka
      and z.ide_zak = '6065'

select @lnOstat = SUM(koruny) from #tmp where sekce = 'REZIE4'
select @lnRezie = SUM(koruny) from #tmp where sekce = 'REZIE3'
select @lnSekce = SUM(koruny) from #tmp where sekce = 'SEKTOR'
select @lnPodil = SUM(koruny) from #tmp

select @lnPodil = isnull(@lnPodil,0) - isnull(@lnOstat,0) - isnull(@lnRezie,0) - isnull(@lnSekce,0) 
drop table #tmp

@lnPodil = 1 623 779.67 の結果を生成します。

つまり、100k の差があり、これはお金に関するものなので、かなりの差があります。解決策を探すのに必死なので、そこで質問しています。SQL 変換は FoxPro のコードを正確に反映していますか?

テーブルは同じなので、データです。SQL では、これらの dbfs にアクセスするためにリンク サーバーを使用しています。フィールド「koruny」は、浮動データ型として dbf に格納されます。

4

2 に答える 2

2

誰かが VFP から SQL サーバーにデータを変換した場合、SQL サーバーにアップロードされていない VFP で削除対象としてマークされたレコードがあるかどうか疑問に思っています。これは、VFP で "SET DELETED ON" を使用して削除対象としてマークされたレコードを非表示にすることで処理されます。「SET DELETED OFF」を使用して、削除されたレコードを表示できるようにします (そして、最終的にはクエリに含めます)。

そうは言っても、SQL から @@rowcount をチェックして、それも一致するかどうかを確認することで、クエリで処理されているレコードの COUNT を確認します。

さて、VFP がどのように動作するか「正確」ではないことがいくつかありますが、確率に基づいて、それ以外は問題ないと思います。それは VFP の「$」に関してです。「$」は、右側の文字列のどこか左側にあるものであると言うのに使用されます...

lcZnak1 = "HM,P6";

WHERE (Zakslozkap.SW $ lcZnak1)

あなたの変換

ここで、p.SW = 'HM' または p.SW = 'P6'

おそらく大丈夫ですが、ここに違いがあります

「M」または「P」、さらには「M」または「P」、さらには「HM、P」、「HM、」、「、」の「SW」列に値があるとしましょう。 P6」など、全員が対象となります。これは、SQL の LIKE コマンドに似ています。下部の合計でも同様です。ただし、探しているものと一致するように列の幅が "x" 文字である場合は、おそらく良好な状態です。

以上のことを踏まえて、変換によるレコードの「削除済み」ステータスを検討します。最初に次のことを行うだけで、VFP サイド クエリをテストすることもできます...

削除済みをオンに設定

残りの var とクエリを実行します。

DELETED ON を使用すると、削除されたレコードを「無視」します。

于 2013-09-08T19:20:08.047 に答える