2015-06-03 5 views
0

Я не могу использовать, где условие на номер строки в пределах одного оператора select. Результаты не соответствуют, если я использую другой оператор выбора для применения условия по RowNumber ...Как иметь предложение where в row_number внутри одного оператора select?

SELECT TOP (@lastrow - 1) c.totalRows 
     ,c.ae_effective_enrollment_id 
     ,c.[user_id] 
     ,c.login_name 
     ,c.first_name 
     ,c.last_name 
     ,cm.courseware_title 
     ,cm.courseware_code 
     ,@courseware_id assetId 
     ,c.enrollment_status_id 
     ,CASE 
      WHEN c.enrollment_status_id = 2 
       AND c.is_self_enrolled = 0 
       THEN 'Admin-' + s.description 
      WHEN c.enrollment_status_id = 2 
       AND c.is_self_enrolled = 1 
       THEN 'Self-' + s.description 
      ELSE s.description 
      END AS enrollmentStatus 
     ,c.is_group 
     ,CASE 
      WHEN c.is_self_enrolled = 0 
       THEN 1 
      ELSE 0 
      END is_admin 
     ,CASE 
      WHEN c.auma_is_assigned = 1 
       THEN 'Admin-assigned' 
      WHEN c.auma_is_assigned = 0 
       THEN 'Self-assigned' 
      ELSE 'No-My-Plan' 
      END AS myplanStatus 
     , master_assignment_id 
     ,ROW_NUMBER() over(partition by cm.courseware_id,c.user_id order by c.is_self_enrolled)as check_row 
    FROM enrollmentCTE c 
    INNER JOIN dbo.courseware_master cm ON cm.courseware_id = @courseware_id 
    LEFT JOIN @statuscodes s ON s.id = c.enrollment_status_id 
    WHERE check_row=1 and 
    enrollment_status_id<>4 and 
    rownumber > @firstrow 
     AND rownumber < @lastrow 
    ORDER BY rownumber 

check_row здесь не признается. Пожалуйста, помогите

+4

Вы должны использовать подзапрос или КТР. Это стандартно - вы не можете ссылаться на псевдоним столбца в 'WHERE' на том же уровне, что и' SELECT', где он определен. –

ответ

0
SELECT totalRows, ae_effective_enrollment_id, user_id, login_name, first_name, last_name, check_row FROM 
(SELECT TOP (@lastrow - 1) c.totalRows as totalRows 
     ,c.ae_effective_enrollment_id as ae_effective_enrollment_id 
     ,c.[user_id] as user_id 
     ,c.login_name as login_name 
     ,c.first_name as first_name 
     ,c.last_name as last_name 
     ,cm.courseware_title as courseware_title 
     ,cm.courseware_code as courseware_code 
     ,@courseware_id as assetId 
     ,c.enrollment_status_id as enrollment_status_id 
     ,CASE 
      WHEN c.enrollment_status_id = 2 
       AND c.is_self_enrolled = 0 
       THEN 'Admin-' + s.description 
      WHEN c.enrollment_status_id = 2 
       AND c.is_self_enrolled = 1 
       THEN 'Self-' + s.description 
      ELSE s.description 
      END AS enrollmentStatus 
     ,c.is_group 
     ,CASE 
      WHEN c.is_self_enrolled = 0 
       THEN 1 
      ELSE 0 
      END is_admin 
     ,CASE 
      WHEN c.auma_is_assigned = 1 
       THEN 'Admin-assigned' 
      WHEN c.auma_is_assigned = 0 
       THEN 'Self-assigned' 
      ELSE 'No-My-Plan' 
      END AS myplanStatus 
     , master_assignment_id 
     ,ROW_NUMBER() over(partition by cm.courseware_id,c.user_id order by c.is_self_enrolled)as check_row 
    FROM enrollmentCTE c 
    INNER JOIN dbo.courseware_master cm ON cm.courseware_id = @courseware_id 
    LEFT JOIN @statuscodes s ON s.id = c.enrollment_status_id 
    WHERE enrollment_status_id<>4 and 
    rownumber > @firstrow 
     AND rownumber < @lastrow 
    ORDER BY rownumber) t where check_row = 1 

Примечание - добавить все имя столбца в первом операторе отбора

2

SQL порядок исполнения.

  1. FROM пункт
  2. WHERE пункт
  3. GROUP пунктом
  4. HAVING пункт
  5. SELECT пункт
  6. ORDER BY пункт

check_row псевдоним был сделан в select части, так что еще не существует в контексте

EDIT сделали некоторые тесты. не может показаться правильным. в качестве временного решения можно попытаться поставить

ROW_NUMBER() over(... 

в пункте where как хорошо

EDIT: другой вариант из MSDN website является

Возвращаясь подмножество строк

В следующем примере вычисляются номера строк для всех строк в SalesOrderHe ader в порядке OrderDate и возвращает только строки от 50 до 60 включительно.

USE AdventureWorks2012; 
GO 
WITH OrderedOrders AS 
(
    SELECT SalesOrderID, OrderDate, 
    ROW_NUMBER() OVER (ORDER BY OrderDate) AS RowNumber 
    FROM Sales.SalesOrderHeader 
) 
SELECT SalesOrderID, OrderDate, RowNumber 
FROM OrderedOrders 
WHERE RowNumber BETWEEN 50 AND 60; 
+0

aliasing in the- вы можете спросить его? –

+0

Это помогло, спасибо :) –

+0

приветствуются – Sarfaraaz

0

Используйте CTE, чтобы сделать запрос на основе другого

;WITH CTE AS(
    SELECT c.totalRows 
      ,c.ae_effective_enrollment_id 
      ,c.[user_id] 
      ,c.login_name 
      ,c.first_name 
      ,c.last_name 
      ,cm.courseware_title 
      ,cm.courseware_code 
      ,@courseware_id assetId 
      ,c.enrollment_status_id 
      ,CASE 
       WHEN c.enrollment_status_id = 2 
        AND c.is_self_enrolled = 0 
        THEN 'Admin-' + s.description 
       WHEN c.enrollment_status_id = 2 
        AND c.is_self_enrolled = 1 
        THEN 'Self-' + s.description 
       ELSE s.description 
       END AS enrollmentStatus 
      ,c.is_group 
      ,CASE 
       WHEN c.is_self_enrolled = 0 
        THEN 1 
       ELSE 0 
       END is_admin 
      ,CASE 
       WHEN c.auma_is_assigned = 1 
        THEN 'Admin-assigned' 
       WHEN c.auma_is_assigned = 0 
        THEN 'Self-assigned' 
       ELSE 'No-My-Plan' 
       END AS myplanStatus 
      , master_assignment_id 
      ,ROW_NUMBER() over(partition by cm.courseware_id,c.user_id order by c.is_self_enrolled) as check_row 
    FROM enrollmentCTE c 
    INNER JOIN dbo.courseware_master cm ON cm.courseware_id = @courseware_id 
    LEFT JOIN @statuscodes s ON s.id = c.enrollment_status_id 
    WHERE enrollment_status_id<>4 
    AND rownumber > @firstrow 
    AND rownumber < @lastrow 
) 
SELECT TOP (@lastrow - 1) * 
FROM CTE 
WHERE check_row = 1 
ORDER BY rownumber 
Смежные вопросы