Как обрабатывать пустые строки в CROSS APPLY [SQL Server]

Я ниже Stored Procedure-

ALTER PROCEDURE [dbo].[Optimized_GetArticlePostAMP]                                                              
(                                                                                    
 @PostID int                                                                                    
)                                                                                          

AS                                                                                    
BEGIN                                                                                    
SET NOCOUNT ON;                                                                                    
SET STATISTICS TIME ON                                                    

DECLARE @SectionId int ,@datediff int                                            
DECLARE @postdate datetime

 SELECT P.PostId, P.SectionID, P.PostName,MP.MetaTitle,P.Postdate,P.PostAuthor,P.IsApproved,                                                                                             
 MP.Metadescription, MP.Metakeywords,ISNULL(MP.IsRobotsMetaTag,0) as IsRobotsMetaTag,p.TotalViews, P.Subject, P.FormattedBody,                                                                                               
 MV.Isvideo,MV.VideoCode,MV.VideoCaption, A.DrComment,A.SpanishURL, PS.RedirectUrl, Isnull(PS.IsRedirect,0) as IsRedirect,                                     
 ISNULL(A.CommentedBy,38633) as CommentedBy ,MP.Canonical as Canonical,ISNULL(MP.RRpopUP ,0) as RRpopUP,ISNULL(A.PrevPost,0) as PreviousPostId,        
 ISNULL(A.NextPost,0) as NextPostId,PS.StatusId ,dbo.[mercola_GetCommentCountForPost](@PostId) as TotalReplies, isnull(PA.[FileName],'') as FileName,         
 PRD.StoryImage, PRD.StoryContent, ISNULL(NULLIF(prd.ALT, ''), P.Subject) AS ALT, ISNULL(PR.ReferenceData,'')as ReferenceData,       
 MH.LastModifiedDate,    
 CASE WHEN CHARINDEX('<p><strong>By', FormattedBody, -1)=1 THEN LTRIM(SUBSTRING(REPLACE(CAST(FormattedBody as varchar(max)),'<p><strong>By ',''),0,CHARINDEX('<',REPLACE(cast(FormattedBody as varchar(max)),'<p><strong>By ',''))))   
 ELSE 'Dr.Mercola' END as Name  
 FROM cs_posts P        
 LEFT JOIN Mercola_NewsletterDetails A on (P.Postid = A.postid)                                                                                       
 LEFT JOIN Mercola_PostStatus PS on (PS.postid=p.postid)                                                    
 LEFT JOIN Mercola_PostMetatags MP on(P.postid=MP.Postid)                                                                                             
 LEFT JOIN Mercola_postVideo MV  on(P.postid=MV.Postid)                                                      
 LEFT JOIN CS_PostAttachments PA on P.PostId=PA.PostId AND PA.contenttype LIKE 'audio/mpeg' AND PA.FILENAME LIKE '%.mp3' AND PA.isremote = 1                                                    
 LEFT JOIN Mercola_PostRelatedData PRD on P.PostId=PRD.PostId                                                  
 LEFT JOIN Mercola_PostReferences PR on P.PostId=PR.PostId        
 CROSS APPLY (select top 1 LastModifiedDate from Mercola_ArticleModifiedHistory where Mercola_ArticleModifiedHistory.Postid = P.postid order by LastModifiedDate desc)MH                                                  
 where P.Postid = @Postid 

Теперь, когда я execute выше SP с ниже PostID -

--[Mercola_Optimized_GetArticlePostAMP] 732490 Я получаю следующие данные, которые expected, Как запрос внутри cross apply есть данные для вышеперечисленного postID,

Но сейчас, когда я execute тот же самый SP с ниже разных PostID -

--[Mercola_Optimized_GetArticlePostAMP] 40702 Я получаю ниже empty data [rows], Как запрос внутри cross apply не имеет данных для вышеперечисленного postID Infact, другой joins есть данные.

Ожидаемый результат для приведенного выше случая - возврат данных и присвоение значения по умолчанию для CROSS APPLY, Как мне это сделать?

2 ответа

Решение

Использование OUTER APPLY вместо CROSS APPLY

Для заполнения NULL используйте ISNULL(MH.LastModifiedDate, @DefaultValue) as LastModifiedDate

Измените ваш запрос на Outer Apply, который сохранит строки с левой стороны, даже если совпадений нет

   outer APPLY (select top 1 LastModifiedDate
    from ArticleModifiedHistory 
    where ArticleModifiedHistory.Postid = P.postid order by LastModifiedDate desc

Крест применяется аналогично Inner Join, так что вы получите только совпадающие строки,Outer apply как Left join которая сохранит вашу левую таблицу, даже если нет соответствующих строк

Обновить:

если вы хотите назначить значение по умолчанию для внешней строки применения в случае нулевого значения, просто используйте IsNull в select

что-то вроде ниже:

select *,isnull(b.id,'defaultvalue') from test1 t1 
outer apply(select id from test2 t2 where t1.id=t2.id) b
Другие вопросы по тегам