1

我正在提取按开始和结束日期过滤的发票列表,并从 SQL 表中按发票类型进一步过滤。当我指定 2013-07-01 到 2013-09-30 的范围时,我预计每家公司收到 2 张发票,而我预计 3 张。当我在 SSMS 中使用内置的 select top 1000 查询并添加我的日期过滤器时,所有预期出现发票。

这是我使用输入变量的奇特查询:

DECLARE @ReportStart datetime
DECLARE @ReportStop datetime

SET @ReportStart = '2013-07-01'
SET @ReportStop = '2013-09-30'

SELECT Entity_Company.CompanyName,
Reporting_AgreementTypes.Description,
Reporting_Invoices.InvoiceAmount,
ISNULL(Reporting_ProductCost.ProductCost,0),
(Reporting_Invoices.InvoiceAmount - ISNULL(Reporting_ProductCost.ProductCost,0)),
(Reporting_AgreementTypes.Description + Entity_Company.CompanyName),
Reporting_Invoices.InvoiceDate
FROM Reporting_Invoices
JOIN Entity_Company ON Entity_Company.ClientID = Reporting_Invoices.ClientID
LEFT JOIN Reporting_ProductCost ON Reporting_ProductCost.InvoiceNumber =Reporting_Invoices.InvoiceNumber
JOIN Reporting_AgreementTypes ON Reporting_AgreementTypes.AgreementTypeID = Reporting_Invoices.AgreementTypeID
WHERE Reporting_Invoices.AgreementTypeID = (SELECT AgreementTypeID FROM Reporting_AgreementTypes WHERE Description = 'Resold Services')
AND Reporting_Invoices.InvoiceDate >= @ReportStart AND Reporting_Invoices.InvoiceDate <= @ReportStop

ORDER BY CompanyName,InvoiceDate

以上仅返回每家公司 2 张发票。当我通过 SSMS 运行更基本的查询时,我得到了 3 的预期结果,如下所示:

SELECT TOP 1000 [InvoiceID]
      ,[AgreementID]
      ,[AgreementTypeID]
      ,[InvoiceDate]
      ,[Comment]
      ,[InvoiceAmount]
      ,[InvoiceNumber]
      ,[TicketID]
      ,Entity_Company.CompanyName
  FROM Reporting_Invoices
  JOIN Entity_Company ON Entity_Company.ClientID = Reporting_Invoices.ClientID
  WHERE Entity_Company.ClientID = '9' AND 
  AgreementTypeID = (SELECT AgreementTypeID FROM Reporting_AgreementTypes WHERE Description = 'Resold Services')

  AND Reporting_Invoices.InvoiceDate >= '2013-07-01' AND Reporting_Invoices.InvoiceDate <= '2013-09-30'

  ORDER BY InvoiceDate DESC

我已经尝试剥离第一个查询,只包含原始发票表中的客户 ID、发票日期,仅包含其他内容。仍然只得到 2 张发票而不是预期的 3 张发票。我也尝试手动输入日期而不是 @ 变量,结果相同。我确认 InvoiceDate 被定义为表中的日期时间。我已经尝试将所有 JOIN 都设为 FULL JOIN,以查看是否隐藏了任何东西,但没有任何变化。以下是我如何剥离原始查询以将所有其他表排除在外,但每个客户 ID 仍然只收到 2 张发票,而不是 3 张(我手动输入了类型过滤器的 ID):

--DECLARE @ReportStart datetime
--DECLARE @ReportStop datetime

--SET @ReportStart = '2013-07-01'
--SET @ReportStop = '2013-09-30'

SELECT --Entity_Company.CompanyName,
--Reporting_AgreementTypes.Description,
Reporting_Invoices.ClientID,
Reporting_Invoices.InvoiceAmount,
--ISNULL(Reporting_ProductCost.ProductCost,0),
--(Reporting_Invoices.InvoiceAmount - ISNULL(Reporting_ProductCost.ProductCost,0)),
--(Reporting_AgreementTypes.Description + Entity_Company.CompanyName),
Reporting_Invoices.InvoiceDate
FROM Reporting_Invoices
--JOIN Entity_Company ON Entity_Company.ClientID = Reporting_Invoices.ClientID
--LEFT JOIN Reporting_ProductCost ON Reporting_ProductCost.InvoiceNumber = Reporting_Invoices.InvoiceNumber
--JOIN Reporting_AgreementTypes ON Reporting_AgreementTypes.AgreementTypeID = Reporting_Invoices.AgreementTypeID
WHERE Reporting_Invoices.AgreementTypeID = '22'-- (SELECT AgreementTypeID FROM Reporting_AgreementTypes WHERE Description = 'Resold Services')
AND Reporting_Invoices.InvoiceDate >= '2013-07-01' AND Reporting_Invoices.InvoiceDate <= '2013-09-30'

ORDER BY ClientID,InvoiceDate

这让我觉得很奇怪,因为它与 SSMS 生成的返回正确结果的查询几乎相同。我在看什么?

更新

我进一步完善了我的“测试查询”,每家公司仅返回 2 张发票,以帮助解决此问题。以下是相应表中 1 家公司的查询和相关数据子集:

SELECT Reporting_Invoices.ClientID,
Reporting_AgreementTypes.Description,
Reporting_Invoices.InvoiceAmount,
Reporting_Invoices.InvoiceDate
FROM Reporting_Invoices
JOIN Reporting_AgreementTypes ON Reporting_AgreementTypes.AgreementTypeID = Reporting_Invoices.AgreementTypeID
WHERE Reporting_Invoices.AgreementTypeID = (SELECT AgreementTypeID FROM Reporting_AgreementTypes WHERE Description = 'Resold Services')
AND Reporting_Invoices.InvoiceDate >= '2013-07-01T00:00:00' AND Reporting_Invoices.InvoiceDate <= '2013-09-30T00:00:00'

ORDER BY Reporting_Invoices.ClientID,InvoiceDate

以上仅退回 2 张发票。以下是相关的表格数据:

Relevant data from Reporting_AgreementTypes         
AgreementTypeID Description     
22              Resold Services     

Relevant data from Reporting_Invoices           
InvoiceID   ClientID    AgreementID AgreementTypeID     InvoiceDate
16111     9         757         22                  2013-09-30 00:00:00.000
15790     9         757         22                  2013-08-30 00:00:00.000
15517     9         757         22                  2013-07-31 00:00:00.000

Actual results from my new modified query           
ClientID    Description InvoiceAmount   InvoiceDate
9           Resold Services 3513.79         7/31/13 00:00:00
9        Resold Services    3570.49         8/30/13 00:00:00
4

2 回答 2

0

要检查的事情:

  • '2013-09-30' 缺少发票吗?
  • InvoiceDate 实际上是带有时间元素的日期时间吗?

如果您正在比较日期时间,则除非指定,否则时间为 00:00,这将排除该日期的大部分时间。如果你想包含它,那么你可以使用

 < '2013-10-01'

或者

 convert(date, InvoiceDate) <= '2013-09-30'
于 2013-10-21T15:27:17.253 回答
0

检查1:你确定你在看同一个数据库吗?检查 SSMS 中的右下角。


检查2:dateformat日期在不同或language选项下意味着不同的事物。例如,日期2013-01-02表示法国的 2 月 1 日:

set language french
select cast('2010-02-01' as datetime)
--> 2010-01-02 00:00:00.000
set language us_english
select cast('2010-02-01' as datetime)
--> 2010-02-01 00:00:00.000
set dateformat ydm
select cast('2010-02-01' as datetime)
--> 2010-01-02 00:00:00.000

您可以显示当前的日期格式选项:

select  s.date_format
,       s.language 
from    sys.dm_exec_sessions s
where   s.session_id = @@spid

将上述查询放在其他两个查询之上并比较结果。


检查 3:打开事务的效果仅在其自己的会话中可见。因此,请检查是否有任何未结交易。你可以这样做:

dbcc opentran

检查 4:该列的类型是否与您要比较的类型不同?如果是这样,SQL Server 会将具有较低优先级的数据类型转换为具有较高优先级的数据类型。

这是一个例子:

create table t1 (dt date);
insert t1 values ('2010-01-01');
select * from t1 where dt = '1 Jan 2010'

这将返回一行,因为date它的优先级高于varchar. 所以'1 Jan 2010'转换为date. 如果反过来,'2010-01-01'就不会匹配 match '1 Jan 2010'

于 2013-10-21T15:31:14.723 回答