【问题标题】:Find Length of longest substring with all 1's in a binary string with k queries在具有 k 个查询的二进制字符串中查找全为 1 的最长子字符串的长度
【发布时间】:2017-12-02 11:57:14
【问题描述】:

给定一个由 0 和/或 1 组成的大小为 n 的字符串。您必须执行 k 个查询,并且可能有 两种 类型的查询。

  1. “1”(不带引号):打印全为'1'的最长子串的长度。
  2. “2 X”(不带引号):其中 X 是 1 到 n 之间的整数。在此查询中,您将第 X 位置的字符更改为 '1'(第 i 位置的字符可能已经是 ' 1')

输入格式:

  • 输入的第一行包含 n 和 k,其中 n 是字符串长度,k 是查询数。
  • 下一行包含长度为 n 的 0 和/或 1 字符串。
  • 接下来的 k 行中的每一行都包含任何一种类型(即 1 或 2)的查询。

输出格式:对于类型 1 的每个查询,在新行中打印子数组的最大大小 全部为 1。

示例输入: 示例输出: 5 7 0 00000 1 1 1 2 3 3 1 2 5 1 2 4 1

我的解决方案:O(k*n)(如果大多数查询类型为 1)

 if(type==1){
        int count=0, ans=0;
        for(int i=0;i<str.size();i++){  //longest len substring
            if(str[i]=='1'){
                count++;
            }else{
               ans=max(ans,count);
               count=0;
            }
        }

        printf("%d\n",ans);
 }else{
        int xth;
        scanf("%d",&xth);
        str[xth-1]='1';   //update
 }

我无法找到一个有效的解决方案,至于“类型 1”查询,我能想到的唯一解决方案是每次遍历字符串并保持一个“计数”变量连续全为 1,最后更新“ans " 当第 i 个 str 变为 '0' 时的变量。

我正在考虑使用分段树,但不知道该怎么做。根据需要,好的解决方案应该是 O(k*log(n)) (在 log(n) 时间内执行“type1”查询)

【问题讨论】:

  • 这是一个相当巧妙的方法来做这个练习。你应该检查xth - 1 没有超出你设置的范围。

标签: algorithm data-structures


【解决方案1】:

这可以使用Disjoint sets datastructure 来解决,您从每个数字开始都是一个空集。

当索引i 处的“0”被翻转为“0”时。检查是否item[i-1] == 1,如果是,则将集合{i} 与包含i-1 的集合连接起来。类似于item[i+1]

由于您从不断开“集合”,因此您可以在计算新集合时缓存“最长子字符串”(通过检查您刚刚创建的新子集现在是否最长,如果是,则存储相关长度)

这个解决方案的时间复杂度是O(1)对于“1”类型的操作,O(alpha(n))对于“2”类型的操作(其中alpha:N-&gt;N是反阿克曼,它是次对数)。

这使您在k 查询中获得了O(k*alpha(n)) 最差情况下的总性能。

所以,对于你的例子:

5 7
Create 5 sets: {1} {2} {3} {4} {5}
 00000
 1
Nothing cached, answer is 0
 2 3
2 and 4 are zeros, so don't connect with anything. Cache biggest length 1 ({3})
 1
1 is cached
 2 5
Flip 5. Don't connect with anything.
 1
1 is cached
 2 4
Flip 4. Join({3},{4}) Since both are 1. Join({3,4},{5}) similarly. Cache 3 (since it's the new size of the set contianing 4 is bigger than 1).
 1
3 is cached.

【讨论】:

    【解决方案2】:

    根据他的解释,绝对完美的@amit 是 c++ 实现
    这里排名是为了保持最大本构 1,因此您可以在 O(1) 时间内返回查询 1,因为 SOl 在更新时将始终具有最大 1

    #include <bits/stdc++.h>
    using namespace std;
    typedef struct subset
    {
        int parent;
        int rank;
    }subset;
    int find(subset subsets[], int i)
    {
        if (subsets[i].parent != i)
            subsets[i].parent = find(subsets, subsets[i].parent);
        return subsets[i].parent;
    }
    void Union(subset subsets[], int x, int y)
    {
        int xroot = find(subsets, x);
        int yroot = find(subsets, y);
        if(subsets[xroot].rank < subsets[yroot].rank)
        {
            subsets[xroot].parent = yroot;
            subsets[yroot].rank += subsets[xroot].rank;
        }
        else if (subsets[xroot].rank > subsets[yroot].rank)
        {
            subsets[yroot].parent = xroot;
            subsets[xroot].rank += subsets[yroot].rank;
        }
        else
        {
            subsets[yroot].parent = xroot;
            subsets[xroot].rank+=subsets[yroot].rank;
        }
    }
    int main()
    {
        ios::sync_with_stdio(false);
        cin.tie(0);
        cout.tie(0);
        int n,k,i,q,t,sol=0;
        cin >> n >> k;
        string s;
        cin >> s;
        cin.ignore();
        subset subsets[n];
        for(i=0;i<n;i++)
        {
            subsets[i].parent = i;
            subsets[i].rank = 0;
            if(s[i]=='1')
            {
                subsets[i].rank = 1;
            }
        }
        for(t=0;t<n;t++)
        {
            if(s[t] == '1' && t!=0 && t!=n-1)
            {
                if(s[t-1] == '1')
                {
                    int x = find(subsets,t-1);
                    int y = find(subsets,t);
                    if(x!=y)
                    {
    
                        Union(subsets,t-1,t);
                        sol = max(sol,max(subsets[x].rank,subsets[y].rank));
                        sol = max(sol,subsets[t].rank);
                    }
                }
                if(s[t+1] == '1')
                {
                    int x = find(subsets,t+1);
                    int y = find(subsets,t);
                    if(x!=y)
                    {
                        Union(subsets,t+1,t);
                        sol = max(sol,max(subsets[x].rank,subsets[y].rank));
                        sol = max(sol,subsets[t].rank);
                    }
                }
            }
            if(s[t] == '1' && t==0 )
            {
                if(s[t+1] == '1')
                {
                    int x = find(subsets,t+1);
                    int y = find(subsets,t);
                    if(x!=y)
                    {
    
                        Union(subsets,t+1,t);
                        sol = max(sol,max(subsets[x].rank,subsets[y].rank));
                        sol = max(sol,subsets[t].rank);
                    }
                }
            }
            if(s[t] == '1' && t==n-1)
            {
                if(s[t-1] == '1')
                {
                    int x = find(subsets,t-1);
                    int y = find(subsets,t);
                    if(x!=y)
                    {
    
                        Union(subsets,t-1,t);
                        sol = max(sol,max(subsets[x].rank,subsets[y].rank));
                        sol = max(sol,subsets[t].rank);
                    }
                }
            }
            sol = max(sol,subsets[t].rank);
        }
        for(i=0;i<k;i++)
        {
            cin >> q;
            if(q==1)
            {
                cout << sol << endl;
            }
            else
            {
                cin >> t;
                t--;
                if(s[t] == '0' && t!=0 && t!=n-1)
                {
                    s[t] = '1';
                    subsets[t].rank = 1;
                    if(s[t-1] == '1')
                    {
                        int x = find(subsets,t-1);
                        int y = find(subsets,t);
                        if(x!=y)
                        {
    
                            Union(subsets,t-1,t);
                            sol = max(sol,max(subsets[x].rank,subsets[y].rank));
                            sol = max(sol,subsets[t].rank);
                        }
                    }
                    if(s[t+1] == '1')
                    {
                        int x = find(subsets,t+1);
                        int y = find(subsets,t);
                        if(x!=y)
                        {
    
                            Union(subsets,t+1,t);
                            sol = max(sol,max(subsets[x].rank,subsets[y].rank));
                            sol = max(sol,subsets[t].rank); 
                        }
                        //Union(subsets,t+1,t);
                    }
                }
                if(s[t] == '0' && t==0 )
                {
                    s[t] = '1';
                    subsets[t].rank = 1;
                    if(s[t+1] == '1')
                    {
                        int x = find(subsets,t+1);
                        int y = find(subsets,t);
                        if(x!=y)
                        {
                            Union(subsets,t+1,t);
                            sol = max(sol,max(subsets[x].rank,subsets[y].rank));
                            sol = max(sol,subsets[t].rank);
                        }
                    }
                }
                if(s[t] == '0' && t==n-1)
                {
                    s[t] = '1';
                    subsets[t].rank = 1;
                    if(s[t-1] == '1')
                    {
                        int x = find(subsets,t-1);
                        int y = find(subsets,t);
                        if(x!=y)
                        {
                            Union(subsets,t-1,t);
                            sol = max(sol,max(subsets[x].rank,subsets[y].rank));
                            sol = max(sol,subsets[t].rank);
                        }
                    }
                }
                sol = max(sol,subsets[t].rank);
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-03
      • 2013-10-29
      • 2021-07-24
      • 2013-12-14
      • 1970-01-01
      相关资源
      最近更新 更多