There are nn people at the round gaming table. Each of them has a set of cards. Every card contains some number xx. Players make turns consecutively, one after another, starting from the player number 1. A player in his turn can either skip his turn (to pass), or put (and leave on the table) a card with a number that is strictly greater than the previously played last number. No more than kk players in a row can pass the turn. All players know the numbers written on the other players cards and always play optimally. Help gamblers to assemble an increasing sequence of maximum length.

Input

The first line contains two numbers nn and kk — the number of players and the maximum possible amount of turn skipping in a row.

The next nn lines contain the description of the cards players have in their hands. The first number in the mimi is the number of cards the current player has in his hand. The following space separated miminumbers represent the written on the cards numbers xx.

0≤∑mi≤1050≤∑mi≤105
1≤n≤1051≤n≤105
0≤k<n0≤k<n
0≤x≤1090≤x≤109

Output

In the first line print the single number — the length of the maximum sequence. In the next lines print two space separated numbers: the player index number and the number written on the card he played. If several solutions exist, output any of them.

Example

Input
3 1
4 1 10 12 20
2 11 21
4 3 5 15 22
Output
9
1 1
3 3
1 10
2 11
1 12
3 15
1 20
2 21
3 22
#include <bits/stdc++.h>
#define ll long long
#define ull unsigned long long
#define met(a, b) memset(a, b, sizeof(a))
#define rep(i, a, b) for(int i = a; i <= b; i++)
#define bep(i, a, b) for(int i = a; i >= b; i--)
#define lowbit(x) (x&(-x))
#define MID (l + r) / 2
#define ls pos*2
#define rs pos*2+1
#define pb push_back
#define ios() ios::sync_with_stdio(0) using namespace std;
typedef pair<int,int>pi;
const int maxn = 1e5 + ;
const int inf = 0x3f3f3f3f;
const ll INF = 0x3f3f3f3f3f3f3f3f;
const ll mod = 1e9 + ; struct node{
int id,x;
bool operator < (const node & w)const{
return x < w.x || (x == w.x && id < w.id);
}
}arr[maxn];
pi dp[maxn],tree[maxn<<];
void pushup(int rt){
tree[rt] = max(tree[rt*],tree[rt*+]);
}
void build(int l,int r,int rt){
if(l == r){
tree[rt] = pi(,-);
return ;
}
int mid = (l + r) / ;
build(l,mid,rt*);
build(mid + ,r,rt*+);
pushup(rt);
}
pi query(int L,int R,int l,int r,int rt){//询问[L,R]内长度最长的上升子序列节点
if(L > R)return pi(,-);
if(L <= l && r <= R){
return tree[rt];
}
int mid = (l + r) / ;
pi ans = pi(,-);
if(L <= mid)ans = max(ans,query(L,R,l,mid,rt*));
if(R > mid)ans = max(ans,query(L,R,mid+,r,rt*+));
return ans;
}
void update(int pos,pi val,int l,int r,int rt){//pos位置更改最优值(和自身取最优值)
if(l == r){
tree[rt] = max(tree[rt],val);
return ;
}
int mid = (l + r) / ;
if(pos <= mid)update(pos,val,l,mid,rt*);
else update(pos,val,mid+,r,rt*+);
pushup(rt);
}
void dfs(int u,int dep){//dfs寻找路径,dp[u].second 代表下一个下标是几
if(u == -){
cout << dep << endl;
return ;
}
dfs(dp[u].second,dep+);
cout << arr[u].id << ' ' << arr[u].x << endl;
}
int main()
{
int n,k,top = ;
cin >> n >> k;
build(,n,);
rep(i,,n){
int m;
cin >> m;
rep(j,,m){
int x;
cin >> x;
arr[++top] = (node){i,x};
}
}
sort(arr+,arr++top);
int i;
for(i = ;i <= top;){
for(int j = i;j <= top;j++){//一个值的数据有多个的话,处理完,先不更新,因为题目保证严格递增
if(arr[i].x != arr[j].x)break;
int id = arr[j].id;
int pos = ((id - k - ) % n + n) % n + ;//最多可跳过k个,这个推一下就好了~
if(pos < id)dp[j] = query(pos,id-,,n,);
else dp[j] = max(query(pos,n,,n,),query(,id-,,n,));
}
int j;
for(j = i;j <= top;j++){
if(arr[i].x != arr[j].x)break;
if(dp[j].first == && arr[j].id > k + )continue;//第一个人特判
dp[j].first++;//以j为结尾的最长上升子序列加1
int pos = arr[j].id;
update(pos,pi(dp[j].first,j),,n,);//更新最优值
}
i = j;
}
int ans = ,rt = ;
for(int i = ;i <= top;i++){
if(dp[i].first > ans){
ans = dp[i].first;
rt = i;
}
}
if(rt == )cout << << endl;
else dfs(rt,);
return ;
}
/*
3 0
3 1 2 3
3 1 2 1
4 1 2 3 2
*/

D - Lis on Circle Gym - 102441D (LIS + 线段树)的更多相关文章

  1. cf1132G 线段树解分区间LIS(一种全新的线段树解LIS思路)+单调栈

    /* 给定n个数的数列,要求枚举长为k的区间,求出每个区间的最长上升子序列长度 首先考虑给定n个数的数列的LIS求法:从左往右枚举第i点作为最大点的贡献, 那么往左找到第一个比a[i]大的数,设这个数 ...

  2. Codeforces Gym 100231B Intervals 线段树+二分+贪心

    Intervals 题目连接: http://codeforces.com/gym/100231/attachments Description 给你n个区间,告诉你每个区间内都有ci个数 然后你需要 ...

  3. Gym 101201J Shopping (线段树+取模)

    题意:给定 n 个物品,然后有 m 个人买东西,他们有 x 元钱,然后从 l - r 这个区间内买东西,对于每个物品都尽可能多的买,问你最少剩下多少钱. 析:对于物品,尽可能多的买的意思就是对这个物品 ...

  4. Hacker Cups and Balls Gym - 101234A 二分+线段树

    题目:题目链接 题意:有编号从1到n的n个球和n个杯子. 每一个杯子里有一个球, 进行m次排序操作,每次操作给出l,r. 如果l<r,将[l,r]范围内的球按升序排序, 否则降序排, 问中间位置 ...

  5. Gym - 101982F 扫描线+线段树

    题目链接:https://codeforces.com/gym/101982/attachments 要你求覆盖奇数次的矩形面积并,每次更新时减去原先的值即可实现奇数次有效,下推时为保证线段长度不变左 ...

  6. 洛谷P3928 Sequence2(dp,线段树)

    题目链接: 洛谷 题目大意在描述底下有.此处不赘述. 明显是个类似于LIS的dp. 令 $dp[i][j]$ 表示: $j=1$ 时表示已经处理了 $i$ 个数,上一个选的数来自序列 $A[0]$ 的 ...

  7. Hdu 3564 Another LIS 线段树+LIS

    Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission( ...

  8. HDU3564 --- Another LIS (线段树维护最值问题)

    Another LIS Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total ...

  9. hdu_3564_Another LIS(线段树+LIS)

    题目连接:http://acm.hdu.edu.cn/showproblem.php?pid=3564 题意:给你N个数的位置.数i的位置为第i个数,比如 0 0 2,表示1插在第0个位置,此时数列为 ...

随机推荐

  1. 十九、SAP查询所有数据库表的所有数据

    一.我们打款SAP自带的一个演示数据库SCARR 二.表结构如下 三.代码如下 四.执行结果如下 我们对比一下数据库的内容,很perfect 不忘初心,如果您认为这篇文章有价值,认同作者的付出,可以微 ...

  2. 干货分享:Academic Essay写作套路详解

    你想过如何中立的表达自己吗?大概只有10%不到的同学,会真正重视这个细节.但很多留学生能顺利写完作文已经不容易,还要注意什么中立不中立的.我知道这个标准,对许多同学有些过分,但很残酷的告诉你,这的确是 ...

  3. 吴裕雄 Bootstrap 前端框架开发——Bootstrap 字体图标(Glyphicons):glyphicon glyphicon-picture

    <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <meta name ...

  4. Docker Ubuntu 例子

    版权所有,未经许可,禁止转载 章节 Docker 介绍 Docker 和虚拟机的区别 Docker 安装 Docker Hub Docker 镜像(image) Docker 容器(container ...

  5. mysql 事务使用教程

    一.什么是事务 事务Transaction,是指作为一个基本工作单元执行的一系列SQL语句的操作,要么完全地执行,要么完全地都不执行.   二.事务的特性       原子性         事务是一 ...

  6. jQuery搜索框输入实时进行查询

    在手机上,我们期望在搜索框中输入数据,能够实时更新查询出来的内容,不需要按回车. 实现方式为: $(".search").bind("input propertychan ...

  7. MySQL笔记 01

    STRUCTURE QUERY LANGUAGE 数据库CRUD操作 DDL: 数据库定义语言,定义数据库数据表结构 CREATE(创建): 创建数据库 CREATE DATABASE 数据库名字; ...

  8. POJ 1013:Counterfeit Dollar

    Counterfeit Dollar Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 42028   Accepted: 13 ...

  9. c 转二进制

    int nData = 1568;//转二进制 for (int i = sizeof(int) * 8 - 1; i >= 0; i--){ if ((nData >>i) &am ...

  10. Neo4j--图形理论基础

    参考 https://www.w3cschool.cn/neo4j/neo4j_graph_theory_basics.html 节点 圆圈表示的是节点.节点是图表的基本单位. 节点可以用来存储数据, ...