Time complexity 时间和空间复杂性(针对特定算法)

Time complexity 时间和空间复杂性(针对特定算法),time-complexity,space-complexity,Time Complexity,Space Complexity,尽管我花了30分钟试图更好地理解时间和空间复杂性,但我仍然无法自信地确定以下算法的复杂性: bool checkSubstr(std::string sub) { //6 OR(||) connected if statement(checks whether the parameter //is among the items in the list) } void checkWords(int start,int end) { int wordList[2] ={0

尽管我花了30分钟试图更好地理解时间和空间复杂性,但我仍然无法自信地确定以下算法的复杂性:

bool checkSubstr(std::string sub)
{
    //6 OR(||) connected if statement(checks whether the parameter
    //is among the items in the list)
}

void checkWords(int start,int end)
{
    int wordList[2] ={0};
    int j = 0;

    if (start < 0)
    {
        start = 0;
    }
    if (end>cAmount)
    {
        end = cAmount -1;
    }
    if (end-start < 2)
    {
        return;
    }
    for (int i = start; i <= end-2; i++)
    {
        if (crystals[i] == 'I' || crystals[i] == 'A')
        {
            continue;
        }
        if (checkSubstr(crystals.substr(i,3)))
        {
            wordList[j] = i;
            j++;
        }
    }
    if (j==1)
    {
        crystals.erase(wordList[0],3);
        cAmount -= 3;
        checkWords(wordList[0]-2,wordList[0]+1);
    }
    else if (j==2)
    {
        crystals.erase(wordList[0],(wordList[1]-wordList[0]+3));
        cAmount -= wordList[1]-wordList[0]+3;
        checkWords(wordList[0]-2,wordList[0]+1);
    }

}
该函数基本上检查整个字符串的子字符串中是否有预定的3个字母,例如SAN字母组合。子字符串长度可以是4-6没有真正的方法来确定,这取决于输入非常确定它不相关,尽管不是100%

我的理由是:

如果字符串中有n个字母,最坏的情况是,我们必须检查每个字母。同样,根据输入,这可以通过3种方式完成

所有6个长度的子字符串:如果是这种情况,函数运行n/6次,每次运行8次还是10次?进程,我认为这意味着它的时间复杂性是存在的。 所有4个长度的子字符串:几乎与上面相同的原因,On。 4和6长度子字符串混合:看不出为什么这会与前2个不同。在…上 至于空间的复杂性,我完全不知所措。然而,我有一个想法: 如果函数在最长时间内递归,则需要: n/4 x一次运行中使用的数量 这让我觉得它应该是开着的。虽然,我不相信这是正确的。我想在这个例子中看到其他人的思维过程可能会帮助我更好地理解如何计算时间和空间的复杂性。 谢谢你抽出时间

编辑:让我提供更清晰的信息。我们将6个不同字母的组合读入一个字符串,这几乎可以是任意长度的任意组合。”“crystals”是字符串,我们正在该字母列表中寻找6种不同的3个字母组合。有点像宝石配对游戏。现在,起始列表不包含匹配项6个预定组合中没有一个首先存在。因此,从那时起匹配的唯一方式就是交换或匹配消失。顶级代码处理交换后,将调用该函数检查匹配项,如果找到匹配项,该函数将在删除字符串的匹配部分后递归

现在让我们看看代码是如何寻找匹配的。要演示两个字母的互换,请执行以下操作:

ABA B-R ZIBno空格或实际字符串中的“-”,用于更好的演示

B和R正在交换。此交换仅影响从第2个字母开始到第7个字母结束的6个字母。换句话说,在交换前后,第一个A和最后一个B可以构成匹配的字母是相同的,因此不需要对包括这些单词在内的匹配进行点检查。因此,一个由6个字母组成的子字符串被发送到检查算法。类似地,如果形成的匹配消失,则从字符串中删除的字母范围为4。所以当我想到一个最坏的情况时,我想象要么1次交换产生一个完整的连锁反应,一直匹配到没有足够的字母形成匹配,要么每一次匹配都发生在一次交换中。同样,我不是说在计算时间和空间复杂度时我们应该这样想,而是说代码是这样工作的。希望这是足够清楚,如果不让我知道,我可以提供更多的细节。还需要注意的是,交换金额和位置是我们读取的输入的一部分

编辑:以下是第一次在顶层调用函数的方式: 校验字swaps[i]-2,swaps[i]+3

子串长度可以是4-6,没有真正的方法来确定,取决于 虽然不是100%,但输入非常确定它不相关

这不是代码所显示的;行if checkSubstrcrystals.substri,3表示子字符串总是正好有3个字符。如果子字符串长度不同,则这是相关的,因为在一般情况下,原始子字符串匹配将降级为ON*M,其中N是开始-结束+1输入字符串的大小,M是正在搜索的子字符串的大小。这是因为在最坏的情况下,您将比较源字符串的N个字符中的每个字符的M个字符

这个答案的其余部分假设子字符串的大小为3,因为代码就是这样显示的

如果子字符串的长度始终为3个字符,则情况有所不同:您基本上可以假定checkSubstr为O1,因为您将始终最多比较3个字符。大部分工作发生在for循环内部,该循环处于打开状态,其中N是end-1-start

在循环之后,在最坏的情况下,当输入一个ifs时,您将从crystal中删除一组字符。假设这是一个由内存中的数组支持的字符串,这是一个OcAmount操作,因为wordList[0]后面的所有元素都必须移位。递归调用总是在大小为4的范围内传递;它不会随着输入的大小而增长或收缩,所以您也可以说存在O1递归调用


因此,时间复杂度为+cAmount,其中N为end-1-start,空间复杂度为O1。

子串长度如何成为输入的一部分?它似乎是硬编码到算法中的:if checkSubstrcrystals.substri,3{…}谢谢你的回答,我补充道
如果您想检查的话,您可以获得关于代码如何工作的更清晰的信息。@user3402183看起来不错。我理解密码。我的答案是一样的。我明白了,谢谢你帮助我。我对你的回答有点怀疑。这很清楚,我理解你的意思,但从逻辑上讲,我似乎无法接受。也许当你有时间的时候,你可以进一步解释它,同时我会继续研究。@user3402183是否有什么特别的东西你不明白,或者你只是觉得很难相信它是线性的?我可以试试,明天再改进我的答案。我不知道如何确定空间复杂度。除此之外,当我考虑它时,我想到了Ocn的时间复杂度,n是字符串中的字母数量,c是一个值约为4-6的系数。尽管我确信我的数学不是100%准确,但我不明白我的逻辑哪里是错误的。另外,据我所知,当我们陈述复杂性时,我们可以忽略常数和系数,只要它们不是很大。所以我把它简化为On,n是字符串中的字符数。