Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Web программирование > SQL, базы данных
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 05.07.2019, 22:56   #1
CMEPTHiK
 
Регистрация: 20.03.2011
Сообщений: 3
По умолчанию блочная выборка

Добрый вечер, уважаемые!
помогите разобраться с такой задачкой:
в таблице существует много строк порядка 26 млн.
особо не важно, что строки из себя представляют. Таблица примерно такая:
Код:
--drop table MyTable;
  create table MyTable (
  primarykey uniqueidentifier not null,
  stolbec1 varchar(max),
  stolbec2 varchar(max)
  )
быстренько добавим 1000 строк:
Код:
declare @it int = 1;
  while(@it<=1000)
  Begin
  insert into MyTable(primarykey,stolbec1,stolbec2) values (NEWID(), '1storka'+convert(varchar,@it),'2storka'+convert(varchar,1000-@it));
  set @it = @it+1;
  End
так вот 1000 строк, нужно получить таблицу:
primarykey остается,
остальные столбцы переводятся в строки и складываются
НО используются не все 1000 строк, а 20, далее ещё 20 и т.д.
primarykey должен быть последним значением из 20, а во втором столбце сложенные столбцы в одну строку.
типа так:
pk | concatStr
0642BD43-14FF-4F5D-B015-D0F1F4A7FE9F | 1storka457,2storka5431storka170,2st orka8301storka962,2storka381storka5 39....

этого я добился с первыми 20-тью записями. А мне надо перебрать все 20-ки в этой 1000

Вопрос можно ли НЕ используя цикл сделать такую таблицу.
Ниже код который получает результат выше:
Код:
select top (1) 
	(convert(uniqueidentifier,(
		select top(1) primarykey 
		from (select top (20) primarykey 
			from  MyTable
			order by convert(varchar(36),primarykey)
			) as dfd
		order by convert(varchar(36),primarykey) DESC
		)
	)
	) as pk,
	(select (stolbec1+','+stolbec2) 
		from MyTable
		order by convert(varchar(36),primarykey) for xml path('') 
	) as concatStr 
  from MyTable
  order by convert(varchar(36),primarykey)
  ;
Кстати, сервер Mssql 2008, поэтому много функций не доступно

Последний раз редактировалось CMEPTHiK; 05.07.2019 в 22:59. Причина: забыл
CMEPTHiK вне форума Ответить с цитированием
Старый 06.07.2019, 10:33   #2
evg_m
Старожил
 
Регистрация: 20.04.2008
Сообщений: 5,515
По умолчанию

Цитата:
А мне надо перебрать все 20-ки в этой 1000
таких будет C(20,1000) =3,39483E+41
и это без учета порядка выбранных 20 строк.
abc, acb, bac, bca, cab, cba считаются за одну.
а вовсе не
Цитата:
строк порядка 26 млн.
ошибка на "несколько" порядков.

вы все еще уверены что вам это надо?
программа — запись алгоритма на языке понятном транслятору
evg_m вне форума Ответить с цитированием
Старый 06.07.2019, 18:58   #3
CMEPTHiK
 
Регистрация: 20.03.2011
Сообщений: 3
По умолчанию

Цитата:
Сообщение от evg_m Посмотреть сообщение
таких будет C(20,1000) =3,39483E+41
и это без учета порядка выбранных 20 строк.
abc, acb, bac, bca, cab, cba считаются за одну.
а вовсе не
ошибка на "несколько" порядков.

вы все еще уверены что вам это надо?
на самом деле 26 млн. по 100 тыс. записей надо именно так.
CMEPTHiK вне форума Ответить с цитированием
Старый 07.07.2019, 20:24   #4
CMEPTHiK
 
Регистрация: 20.03.2011
Сообщений: 3
По умолчанию можно закрывать

Ответ дали на другом форуме.
Примерно так:
Код:
--drop table MyTable;
  create table MyTable (
  id uniqueidentifier not null,
  s1 varchar(max),
  s2 varchar(max)
  )

  declare @it int = 1;

  while(@it<=10000000)
  Begin
  insert into MyTable(id,s1,s2) values (NEWID(), '1storka'+convert(varchar,@it),'2storka'+convert(varchar,100-@it));
  set @it = @it+1;
  End;

 if object_id('tempdb..#tmpTable', 'U') is not null
 drop table #tmpTable;
 

--Формирование временной таблицы и результата
if object_id('tempdb..#t', 'U') is not null
 drop table #t;
 
select id, s1, s2, (row_number() over (order by convert(varchar(36),id)) - 1) / 100000 as g into #t from MyTable;--10 - это количество строк в странице
create unique clustered index UCIX_#t on #t (g, id);

select
 a.id, stuff(b.x.value('.', 'varchar(max)'), 1, 2, 'prefix(') as strPage
 into #tmpTable
from
 (select g, max(convert(varchar(36),id)) from #t group by g) a(g, id) cross apply
 (
  select
   ',(' + 
   convert(varchar(max),isnull(s1,'')) + 
   ', ' + 
   convert(varchar(max),isnull(s2,'')) +
   ')'
  from
   #t
  where
   g = a.g
	order by
 convert(varchar(36),id)
  for xml path(''), type
 ) b(x)
order by
 convert(varchar(36),a.id);

/*объявляем переменные*/
DECLARE @strPage varchar(max);
/*объявляем курсор, в котором будут авторы и названия книг, изданных не ранее 2000 года*/
DECLARE cursorl CURSOR FAST_FORWARD
FOR
SELECT strPage FROM #tmpTable
/*открываем курсор и "пробегаем" его, выводя автора и название отдельным оператором SELECT*/
OPEN cursorl
FETCH NEXT FROM cursorl INTO @strPage
WHILE @@FETCH_STATUS = 0
BEGIN
DECLARE @sql varchar(max);
set @sql = convert(varchar(36),(SELECT @strPage));
FETCH NEXT FROM cursorl INTO @strPage;
END
/*закрываем курсор и освобождаем его*/
CLOSE cursorl
DEALLOCATE cursorl
CMEPTHiK вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Блочная сортировка vova287 Общие вопросы C/C++ 3 25.10.2011 14:42
Блочная сортировка oniya Общие вопросы C/C++ 1 19.08.2010 22:58
Блочная верстка Demonichka HTML и CSS 2 12.07.2008 01:31