zoukankan      html  css  js  c++  java
  • CCF CSP认证 201812-3 CIDR合并 (01Trie) (100分)

    所有的ip前缀可以构成一棵01Trie,每个ip地址对应Trie上的一棵叶子结点,那么题意就是选出尽可能少的结点,使其子树中包含所有给出前缀的叶子结点,dp即可

    非标准解法,没看提示,被卡内存了很难受~~

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 typedef long long ll;
     4 const int N=4e7+10,inf=0x3f3f3f3f;
     5 int n,ch[N][2],ed[N],tot;
     6 int newnode() {int u=++tot; ch[u][0]=ch[u][1]=ed[u]=0; return u;}
     7 typedef vector<string> Vec;
     8 Vec split(string S,char C) {
     9     Vec vec;
    10     string s;
    11     for(char c:S) {
    12         if(c!=C)s.push_back(c);
    13         else vec.push_back(s),s.clear();
    14     }
    15     vec.push_back(s),s.clear();
    16     return vec;
    17 }
    18 int rev(int x,int n) {int ret=0; for(int i=0; i<n; ++i)ret=ret<<1|(x>>i&1); return ret;}
    19 int keep(int x,int d) {return x&((1<<d)-1);}
    20 struct IP {int x,l;};
    21 IP strtoIP(string s) {
    22     Vec vec=split(s,'/');
    23     int l=-1;
    24     if(vec.size()==2)sscanf(vec[1].c_str(),"%d",&l);
    25     vec=split(vec[0],'.');
    26     if(l==-1)l=8*vec.size();
    27     int x=0;
    28     for(int i=0; i<vec.size(); ++i) {
    29         int y;
    30         sscanf(vec[i].c_str(),"%d",&y);
    31         x|=rev(y,8)<<(8*i);
    32     }
    33     return {x,l};
    34 }
    35 string IPtostr(IP ip) {
    36     int a[4];
    37     char buf[25];
    38     for(int i=0; i<4; ++i)a[i]=rev(keep(ip.x>>(8*i),8),8);
    39     sprintf(buf,"%d.%d.%d.%d/%d",a[0],a[1],a[2],a[3],ip.l);
    40     return string(buf);
    41 }
    42 void ins(IP ip) {
    43     int u=1;
    44     for(int i=0; i<ip.l; ++i) {
    45         int f=ip.x>>i&1;
    46         if(!ch[u][f])ch[u][f]=newnode();
    47         u=ch[u][f];
    48     }
    49     ed[u]=1;
    50 }
    51 void dfs1(int u) {
    52     if(!u)return;
    53     dfs1(ch[u][0]),dfs1(ch[u][1]);
    54     ed[u]=ed[u]||(ed[ch[u][0]]&&ed[ch[u][1]]);
    55 }
    56 void dfs2(int u,IP ip) {
    57     if(!u)return;
    58     if(ed[u]) {cout<<IPtostr(ip)<<endl; return;}
    59     dfs2(ch[u][0], {ip.x,ip.l+1}),dfs2(ch[u][1], {ip.x|(1<<ip.l),ip.l+1});
    60 }
    61 
    62 int main() {
    63     scanf("%d",&n);
    64     char buf[100];
    65     tot=0,newnode();
    66     while(n--) {
    67         scanf("%s",buf);
    68         string s=buf;
    69         IP ip=strtoIP(s);
    70         ins(ip);
    71     }
    72     dfs1(1);
    73     dfs2(1, {0,0});
    74     return 0;
    75 }
  • 相关阅读:
    使用Picture Control显示BMP图片
    [转]程序员技术练级攻略
    自绘控件笔记
    VS2010中CMFCToolBar的用法
    我用到的FireFox浏览器插件
    C# 中的 DataTimePicker 控件的时间转换
    MacBook 小白,安装 JDK
    C# Combobox 设置选中项
    Drupal7(2)
    Drupal7(1)
  • 原文地址:https://www.cnblogs.com/asdfsag/p/13610211.html
Copyright © 2011-2022 走看看