В таком случае у меня есть еще один. Это то же самое, что и раньше. Результаты не были тем, что мне нужно, поэтому вернулись к чертежной доске. Одинаковые:TSQL date сравнение возвращает ошибочный текст центральная ошибка
SQL Server 2005 || Excel 2007 || Студия SQL Management 2008R2
У меня проблема с двумя датами. Ошибка, которую бросает SSMS, не имеет смысла. Вот код:
declare @calendar_start char(8)
declare @years int
set @calendar_start = '20130101'
set @years = 1
----------------------------------------------------------------------------
-- standard declaration stuff. -
----------------------------------------------------------------------------
-- for ease of entry, I convert the start timeto a real time ---------------
----------------------------------------------------------------------------
declare @startdate datetime
set @startdate = CONVERT (datetime, @calendar_start, 112)
-- to calculate the end of the forecast, I use the start date and add the --
-- provided number of year -------------------------------------------------
----------------------------------------------------------------------------
declare @enddate datetime
set @enddate = dateadd(year,[email protected],@startdate)
----------------------------------------------------------------------------
-- I need a variable to advance the plotting month. the plotting month is --
-- how I am going to spread out the project all year from a single date ----
----------------------------------------------------------------------------
declare @counter int
set @counter = 0
----------------------------------------------------------------------------
----------------------------------------------------------------------------
-- this table will be used to have all the calendar dates by year-month ----
----------------------------------------------------------------------------
create table #calendar (calenderid char(6))
insert into #calendar
select
distinct left(calendarid,6) [yearmonth]
from
[cmdb_core].[dbo].[Calendar]
where
datevalue between @startdate and @enddate
----------------------------------------------------------------------------
----------------------------------------------------------------------------
-- rather than hitting the database any number of times, I load the whole --
-- of the computed estimates table into memory. it is faster that way. ----
----------------------------------------------------------------------------
create table #baseline (
[adjusted_ExpectedActionDt] datetime
,[key] text
,projectid text
,projectnm text
,ParentChaseProjectNo text
,VersionTag text
,itemid text
,Qty int
,ItemNotes text
,CashflowType text
,frequency text
,UnitPrice float
,[cost] float
)
insert into #baseline (
[adjusted_ExpectedActionDt]
,[key]
,projectid
,projectnm
,ParentChaseProjectNo
,VersionTag
,itemid
,Qty
,ItemNotes
,CashflowType
,frequency
,UnitPrice
,[cost]
)
select
case
when (ExpectedActionDt is not null)
then ExpectedActionDt
when (IntegratedReleasePlanDt is not null)
then IntegratedReleasePlanDt
else
DATEADD(YEAR, DATEDIFF(YEAR, 0, GETDATE()), 0)
end [adjusted_ExpectedActionDt]
,cast(ModelEstimateId as nvarchar(max))+cast(BucketId as nvarchar(max))+cast(ItemNo as nvarchar(max)) [key]
,projectid
,projectnm
,ParentChaseProjectNo
,VersionTag
,itemid
,Qty
,ItemNotes
,CashflowType
,frequency
,UnitPrice
,null [cost]
from
estimate.ComputedEstimates
where
[status] <> 'Hold'
and CostCategory <> 'Assembly'
and includeinforecast = 'Y'
and cashflowtype <> 'Notional'
and Qty <> 0
and case
when (ExpectedActionDt is not null)
then ExpectedActionDt
when (IntegratedReleasePlanDt is not null)
then IntegratedReleasePlanDt
else
DATEADD(YEAR, DATEDIFF(YEAR, 0, GETDATE()), 0)
end between @startdate and @enddate
--------------------------------------------------------------------------
--------------------------------------------------------------------------
-- we need a place to contain the results of the interation through the --
-- baseline temp table. the results table will be that. ------------------
--------------------------------------------------------------------------
create table #results (
[adjusted_ExpectedActionDt] datetime
,[plot_date] datetime
,[key] text
,projectid text
,projectnm text
,ParentChaseProjectNo text
,VersionTag text
,itemid text
,Qty int
,ItemNotes text
,CashflowType text
,frequency text
,UnitPrice float
,[cost] float
)
-- this loop is how we will build the results. it is governed by the -----
-- date. as I iterate through the loop, I incriment the plot date so -----
-- that I can show a project and it's costs over the range of dates ------
-- rather than only the month it goes into production --------------------
--------------------------------------------------------------------------
WHILE (@startdate <= @enddate)
BEGIN
insert into #results (
[adjusted_ExpectedActionDt]
,[plot_date]
,[key]
,projectid
,projectnm
,ParentChaseProjectNo
,VersionTag
,itemid
,Qty
,ItemNotes
,CashflowType
,frequency
,UnitPrice
,[cost]
)
select
[adjusted_ExpectedActionDt]
,dateadd(month,[email protected],[adjusted_ExpectedActionDt])
,[key]
,projectid
,projectnm
,ParentChaseProjectNo
,VersionTag
,itemid
,Qty
,ItemNotes
,CashflowType
,frequency
,UnitPrice
,case
when frequency = 'OneTime'
then
--=====================================================================--
--===================== this is where the problem is ==================--
--=====================================================================--
case
when dateadd(mm, datediff(mm,0, [adjusted_ExpectedActionDt]), 0) =
dateadd(mm, datediff(mm,0, dateadd(month,[email protected],[adjusted_ExpectedActionDt])), 0)
then [Qty]
else
0
end
--=====================================================================--
--=====================================================================--
else
cast(round((UnitPrice*Qty)/12,0) as int)
end [cost]
from #baseline
set @counter = @counter+1
set @startdate = dateadd(month,+1,@startdate)
END
--------------------------------------------------------------------------
--------------------------------------------------------------------------
-- now we have to return the results but it is not enough to just dump ---
-- the table, I have to add a date that covers all month regardless of ---
-- that month's presence in the results table. I use the calendar temp, --
-- which has those dates as a basis of the outer join --------------------
--------------------------------------------------------------------------
select
c.calenderid
,r.[adjusted_ExpectedActionDt]
,r.[plot_date]
,r.[key]
,r.projectid
,r.projectnm
,r.ParentChaseProjectNo
,r.VersionTag
,r.itemid
,r.Qty
,r.ItemNotes
,r.CashflowType
,r.frequency
,r.UnitPrice
,r.[cost]
from
#calendar c
left outer join
#results r
on c.calenderid = cast(year(r.[adjusted_ExpectedActionDt])as char(4))+RIGHT('0'+ CONVERT(VARCHAR,month(r.[adjusted_ExpectedActionDt])),2)
--------------------------------------------------------------------------
GO
Проблема заключается в том:
--=====================================================================--
--===================== this is where the problem is ==================--
--=====================================================================--
case
when dateadd(mm, datediff(mm,0, [adjusted_ExpectedActionDt]), 0) =
dateadd(mm, datediff(mm,0, dateadd(month,[email protected],[adjusted_ExpectedActionDt])), 0)
then [Qty]
else
0
end
--=====================================================================--
--=====================================================================--
Когда я пытаюсь запустить этот код, я получаю следующее сообщение об ошибке:
Msg 402, Level 16, State 1, Line 149
The data types text and varchar are incompatible in the equal to operator.
Это наиболее vexxing как Сравнение - это совпадение даты, а не текст. Это я пробовал: 1. много интернет-поиска 2. изменение оператора case в оператор if, но не получило правильного синтаксиса. 3. Изменение даты на датуpart функции только потянув год. мы знаем, что должны возвращать int 4. изменить сравнение на «1 = 1», которое явно является номером и должно всегда быть истинным. 5. попытался конвертировать в конкатенированный текст (yyyymm) 6. поговорил с одним из наших разработчиков SQL (которые я не по названию, но ожидают, что к концу этого проекта :))
действительно странно, что этот общий код работает
select
dateadd(mm, datediff(mm,0, getdate()), 0)
,dateadd(mm, datediff(mm,0, getdate()+60), 0)
,case
when dateadd(mm, datediff(mm,0, getdate()), 0) =
dateadd(mm, datediff(mm,0, getdate()+60), 0)
then 'matches'
else
'different'
end
последний бит информации, что если я комментирую код нарушения, оставляющий только поле [Qty], работает нормально.
помогите мне, Оби, любой, ты моя единственная надежда. Заранее спасибо.
Плохие планы выполнения могут иногда иметь интересные побочные эффекты. Отправьте план выполнения этого запроса. – GSerg
Планы выполнения не работают или не создают ничего для плохого кода. когда я выключить NOCOUNT, я получаю это: это ошибка компиляции (13 строк (ы) пострадавших) (1 ряд (ы) пострадавших) (6620 строк (ы) пострадавших) (1 ряд (s)) Msg 402, уровень 16, состояние 1, строка 146 Текст типов данных и varchar несовместимы в равном оператору. это ошибка компиляции –
Я думаю, нам понадобится больше контекста (где используется CASE, а также типы данных всех столбцов), чтобы выяснить, почему вы получаете ошибку. Но ваше выражение просто похоже на тестирование: @ counter = 0. – GilM