Frage

Ich bin Java -Entwickler. Ich habe ein altes Programm in Delphi. In der alten Version arbeiten sie mit mdb. Ich habe es für die Verbindung mit SQL Server behoben. Alle SQL -Abfragen werden mit implementiert TAdoQuery.

qryTemp.SQL.Text:='select  sum(iif(ComeSumm>0,comesumm,0)),sum(iif(lostSumm>0,lostsumm,0)) from cash '+
   'where (IdCashClause is null or idcashclause<>8) '+
  ' and cashNum='+IntToStr(i)+
  ' and CashType=0'+
  ' and format(PayDate,"dd/mm/yyyy")=format('''+DateToStr(Date)+''',"dd/mm/yyyy") ';

Das Programm bringt eine Ausnahme aus:

Ungültiger Spaltenname 'DD/MM/JJJJ'.

Ich habe andere Anfragen zum Vergleich behoben:

 qryTemp.SQL.Text:=' select top 1 iif(ComeSumm>0,comesumm,0) from cash '
                     +' where idCashReason=1 and idCashClause=8 and cashNum='+IntToStr(i)
                     +' and PayDate<:D'
                     +' order by payDate desc';
qryTemp.Parameters.ParamByName('D').Value:=DateTimeToStr(Date);

Kann ich schnell alle Abfragen für die Arbeit mit SQL Server beheben, ohne das gesamte Projekt neu zu schreiben?

War es hilfreich?

Lösung

Annahme PayDate ist definiert als date/datetime In MSSQL können Sie Parameter wie folgt verwenden:

qryTemp.SQL.Text:=' select top 1 iif(ComeSumm>0,comesumm,0) from cash '
                     +' where idCashReason=1 and idCashClause=8 and cashNum='+IntToStr(i)
                     +' and PayDate<:D'
                     +' order by payDate desc';
qryTemp.Parameters.ParamByName('D').Value := Date;
qryTemp.Parameters.ParamByName('D').DataType := ftDateTime;

Ich würde mich auch ändern cashNum zum Parameter dh:

...
+' where idCashReason=1 and idCashClause=8 and cashNum=:cashNum'+
...
qryTemp.Parameters.ParamByName('cashNum').Value := i;

Verwenden Sie immer kompatible Datentypen mit Ihren Parametern, anstatt Zeichenfolgen zu formatieren und zu verwenden. SQL muss Ihre Datentypen nicht erraten, wenn Sie sie explizit definieren können.

Notiz: IIF wurde in SQL Server 2012 eingeführt. Für die ältere Version verwendet FALL Ausdruck.


Bei älteren nicht-nicht-Unicode-Delphi-Versionen haben Parameter mit Unicode Probleme.
Also wenn du nicht Verwenden Sie Parameter Sie können Folgendes verwenden:

function DateTimeToSqlDateTime(const DT: TDateTime): WideString;
begin
  Result := FormatDateTime('yyyy-MM-dd', DT) + ' ' + FormatDateTime('hh:mm:ss', DT);
end;

function SqlDateTimeStr(const DT: TDateTime; const Is_MSSQL: Boolean): WideString;
var
  S: WideString;
begin
  S := DateTimeToSqlDateTime(DT);
  if Is_MSSQL then
    Result := Format('CONVERT(DATETIME, ''%s'', 102)', [S]) 
  else
    Result := Format('#%s#', [S]); // MS-ACCESS
end;

Und Ihre Frage wird wie folgt aussehen:

...
+' and PayDate<' + SqlDateTimeStr(Date, True)
...

Andere Tipps

Es ist sehr wahrscheinlich, dass die PayDate Die Spalte wird als als deklariert als als DATE in dem cash Tisch. In Anbetracht dessen sollte Ihr Parameter a sein TDateTime und nicht a string, so was:

qryTemp.SQL.Text:=' select top 1 iif(ComeSumm>0,comesumm,0) from cash '
                     +' where idCashReason=:cashReason and idCashClause=8 and cashNum='+IntToStr(i)
                     +' and PayDate<:D'
                     +' order by payDate desc';
qryTemp.Parameters.ParamByName('D').Value := Date;

Ich habe nur einen der Parameter ersetzt, aber Sie sollten in Betracht ziehen, alle zu ersetzen, da dies die Serverleistung verbessert, indem Sie den Satzcache aktivieren.

Wenn Sie auf Ihre ursprüngliche Frage zurückkehren, besteht der einzige Weg, um die gesamte Anwendung neu zu überarbeiten, darin, ein Refactoring -Programm zu haben, das Ihren Code analysieren, diese Situationen finden und ein Muster folgen könnte, um ein Stück Code durch einen anderen zu ersetzen.

Ich kenne kein Werkzeug, das das jetzt jetzt tun kann.

Vielleicht kann es Ihnen helfen, mit Find/Ersatz, das regelmäßige Ausdrücke unterstützt, zu verwenden, aber es wird die Fälle in einem einzigen Pass sicherlich nicht behoben. Sie müssten eine Reihe von Ersatzphasen ausführen, um Ihren Code von dem zu verwandeln, was Sie möchten.

DateToStr verwendet Lokalisierungsinformationen, die in globalen Variablen enthalten sind, um die Datumszeichenfolge zu formatieren. Vielleicht ist das das Problem.

Sie können versuchen, formatDatetime zu sein:

qryTemp.SQL.Text:='select  sum(iif(ComeSumm>0,comesumm,0)),sum(iif(lostSumm>0,lostsumm,0)) from cash '+
   'where (IdCashClause is null or idcashclause<>8) '+
  ' and cashNum='+IntToStr(i)+
  ' and CashType=0'+
  ' and format(PayDate,"dd/MM/yyyy")='''+FormatDateTime('dd/mm/yyyy',Date)+'''';
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top