【问题标题】:Split string into minimal number of strings where each letter is repeated an odd number of times将字符串拆分为最少数量的字符串,其中每个字母重复奇数次
【发布时间】:2020-10-17 13:01:43
【问题描述】:

例如,字符串 "abab" 需要一个拆分成两个字符串:"ab""ab" 所以答案是1 和字符串 "ababab" 不需要任何拆分,所以答案是 0

我想出了一个解决方案,它检查每个子字符串的条件并将结果存储在一个布尔矩阵中,然后填充一个 int 矩阵,以便找到最小的分割数。关于如何使算法更快的任何想法?

bool condition(const int count[]) {
    for (int i = 0; i <= 25; i++){
        if (count[i] != 0 && count[i] % 2 == 0) {
            return false;
        }
    }
    return true;
}



int minPartion(std::string& str)
{
    int n = str.size();


    int i, j, k, L;

    int** even = new int*[n];
    for(int i = 0; i < n; ++i)
        even[i] = new int[n];

    int** minSplits = new int*[n];
    for(int i = 0; i < n; ++i)
        minSplits[i] = new int[n];

    for (i = 0; i < n; i++)
    {
        even[i][i] = true;
        minSplits[i][i] = 0;
    }


    for (int i = 0; i < n; i++) {
        int count2[26] = {0};
        for (int j = i; j < n; j++) {
            count2[str[j] - 'a']++;
            even[i][j] = condition(count2);
        }
    }



    for (L = 2; L <= n; L++)
    {
        for (i = 0; i < n - L + 1; i++)
        {
            j = i + L - 1;

            if (even[i][j])
                minSplits[i][j] = 0;
            else
            {
                minSplits[i][j] = INT_MAX;
                for (k = i; k <= j - 1; k++)
                    minSplits[i][j] = min(minSplits[i][j], minSplits[i][k] + minSplits[k + 1][j] + 1);
            }
        }
    }
    
    return minSplits[0][n - 1];
}

【问题讨论】:

  • 你的意思是奇数次,对吧?
  • 是的,我就是这个意思。

标签: string algorithm matrix dynamic split


【解决方案1】:

一个简单的起点是将计数数组打包成两个 32 位字,一个表示哪些值非零,一个表示哪些值是奇数。您可以分别使用|= uint32_t{1} &lt;&lt; (letter - 'a')^= uint32_t{1} &lt;&lt; (letter - 'a') 更新它们,然后condition 成为一个简单的相等测试。

【讨论】:

  • 条件应该怎么写?
  • @CadeyLewis nonzeros == odds
  • @CadeyLewis 您可以尝试根据需要而不是按顺序计算 minSplits 的行(即计算第 0 行,然后根据哪个 j 是第一个奇数词的可行端点,计算那些,等等)我不得不说这里的结构定理并没有跳出来。如果这是一个公共问题,那么链接原始描述可能会有所帮助。
  • 好吧,我猜这个技巧在这里行不通,因为我们总是可以一次啃 1 个字母 :(
猜你喜欢
  • 2016-01-16
  • 2016-07-23
  • 2013-08-19
  • 1970-01-01
  • 1970-01-01
  • 2019-04-02
  • 1970-01-01
  • 2012-09-11
  • 1970-01-01
相关资源
最近更新 更多