使用sql自动分配队列

时间:2015-11-12 23:14:40

标签: sql sql-server tsql sql-server-2008-r2

我有一张每周工作时间更新的表格。

然后有人拉下表,根据已分配的数字和类型分配QueueT为空的值。

将其视为排队系统,尽可能均匀地均衡工作流程。

我坚持尝试自动化作业

http://sqlfiddle.com/#!3/6a657/1

显示为每个人分配了多少,但我如何更新表格以根据类型甚至分配尽可能多地分配每个人?

  -- create temp table code if needed

create table #tempqueue

(
    QueueT varchar(20)
    ,Type varchar(20)
)

insert into #tempqueue
(
    QueueT 
    ,Type 
)

values
( 'bob' , 'type1'),
( 'bob' , 'type1'),
( 'john' , 'type2'),
( 'john' , 'type2'),
( 'john' , 'type2'),
( 'null' , 'type1'),
( 'null' , 'type1'),
( 'null' , 'type1'),
( 'null' , 'type1'),
( 'null' , 'type2'),
( 'null' , 'type2'),
( 'tim' , 'type1'),
( 'bob' , 'type1'),
( 'jill' , 'type2'),
( 'jack' , 'type2'),
( 'john' , 'type2'),
( 'null' , 'type1'),
( 'null' , 'type1'),
( 'null' , 'type1'),
( 'null' , 'type1'),
( 'null' , 'type2'),
( 'null' , 'type2'),
( 'null' , 'type2')


select


    QueueT 
    ,type
    ,count(Type) counttype

from #tempqueue


group by 
    QueueT 
    ,type

1 个答案:

答案 0 :(得分:1)

首先,您需要表的唯一ID,以便每个记录可以单独更新:

create table tempqueue

(
    id int identity(1,1)
    ,QueueT varchar(20)
    ,Type varchar(20)
)

然后,您可以使用几个子查询mincountrow_number窗口函数来更新它:

create table tempqueue

(
    id int identity(1,1)
    ,QueueT varchar(20)
    ,Type varchar(20)
)

insert into tempqueue
(
    QueueT 
    ,Type 
)

values
( 'bob' , 'type1'),
( 'bob' , 'type1'),
( 'john' , 'type2'),
( 'john' , 'type2'),
( 'john' , 'type2'),
( null , 'type1'),
( null , 'type1'),
( null , 'type3'),
( null , 'type1'),
( null , 'type2'),
( null , 'type2'),
( 'tim' , 'type1'),
( 'bob' , 'type1'),
( 'jill' , 'type2'),
( 'jack' , 'type2'),
( 'john' , 'type2'),
( null , 'type1'),
( null , 'type1'),
( null , 'type1'),
( null , 'type1'),
( null , 'type2'),
( null , 'type2'),
( null , 'type2')

-- loop through records until no records are updated
declare @rows_updated int = 1
while @rows_updated > 0
    begin
        update t
            set t.QueueT = u.QueueT
            from tempqueue t
                -- get min record id per type where QueueT is null
                inner join (select Type,min(id) id
                            from tempqueue
                            where QueueT is null
                            group by Type) id
                    on id.Type = t.Type
                    and id.id = t.id
                -- get QueueT for each Type with the least count
                inner join (select QueueT,Type,
                                row_number() over(partition by Type order by cnt) lst
                            from (select QueueT,Type,count(*) cnt
                                  from tempqueue
                                  where QueueT is not null
                                  group by QueueT,Type)c)u
                    on u.Type = id.Type
                    and u.lst = 1
            set @rows_updated = @@rowcount
    end

select QueueT,Type,count(*) cnt
from tempqueue
group by QueueT,Type

SQL FIDDLE