rt
#include<bits/stdc++.h>
using namespace std;
#define endl '\n'
const int N=2e5+15;
struct edge{
int to,next;
}e[N<<1];
int head[N],low[N],dfn[N],n,m,dcccnt,dfncnt;
bool cut[N];
void addedge(int u,int v){
static int cnt=1;
e[cnt]={v,head[u]};
head[u]=cnt++;
}
stack<int>st;
vector<int>dcc[N];
void Tarjan(int u,int root){
low[u]=dfn[u]=++dfncnt;
st.push(u);
if(u==root&&!head[u]){
dcc[++dcccnt].push_back(u);
return;
}
int f=0;
for(int i=head[u];i;i=e[i].next){
int to=e[i].to;
if(!dfn[to]){
Tarjan(to,root);
low[u]=min(low[u],low[to]);
if(low[to]>=dfn[u]){
dcccnt++;
int x;
do{
x=st.top();
dcc[dcccnt].push_back(x);
st.pop();
}while(x!=to);
dcc[dcccnt].push_back(u);
}
}
else low[u]=min(low[u],dfn[to]);
}
}
signed main(){
cin>>n>>m;
for(int i=1;i<=m;i++){
int u,v;
cin>>u>>v;
addedge(u,v);
addedge(v,u);
}
for(int i=1;i<=n;i++){
if(!dfn[i]){
Tarjan(i,i);
}
}
cout<<dcccnt<<endl;
for(int i=1;i<=dcccnt;i++){
cout<<dcc[i].size()<<' ';
for(auto p:dcc[i]){
cout<<p<<' ';
}
cout<<endl;
}
return 0;
}