以下代码尝试在K次运行中生成随机字符串。 但我们希望新生成的字符串完全不同 带有参考字符串。

为此我尝试使用“继续”重启随机 字符串生成过程。但它似乎不起作用。 我的方法下面有什么问题?

#include <iostream>
#include <vector>
#include <fstream>
#include <sstream>
#include <time.h>
using namespace std;


// In this code we want to print new string that is entirely different with  
// with those in initVector 


template <typename T> void  prn_vec(std::vector < T >&arg, string sep="")
{   // simple function for printing vector
    for (int n = 0; n < arg.size(); n++) {
        cout << arg[n] << sep; 
    }
}


int main  ( int arg_count, char *arg_vec[] ) {

    // This is reference string
    vector <string> initVec;
    initVec.push_back("A");
    initVec.push_back("A");
    initVec.push_back("A");
    initVec.push_back("A");

    vector <string> DNA;
      DNA.push_back("A");
      DNA.push_back("C");
      DNA.push_back("G");
      DNA.push_back("T");

    for (unsigned i =0; i< 10000; i++) {

       vector <string> newString;
       for(unsigned j=0; j<initVec.size(); j++) {

         int dnaNo = rand() % 4;
         string newBase = DNA[dnaNo];
         string oldBase = initVec[j];

         int sameCount = 0;
         if (newBase == oldBase) {
            sameCount++;
         }

         if (sameCount == initVec.size()) {
              continue;
         }

         newString.push_back(newBase);

       } 
       cout << "Run " << i << " : ";
       prn_vec<string>(newString);
       cout << endl;

    }

    return 0;
}
有帮助吗?

解决方案

乍一看,您的代码看起来很好,除非我错过了您的大部分要求。 在使用 rand()之前,请阅读。当然, continue 部分除外。你要做的是看看它是否与 initVector 相同,对吧?在将其推入或打印到控制台之前,可以进行简单的比较。

int sameCount = 0;
if (newBase == oldBase) {
 sameCount++;
}
// sameCount can be 1 at most, 0 otherwise
// this check never return true
if (sameCount == initVec.size()) {
continue;
}

sameCount 变量在每次创建 newString 的新条目时初始化,并且在结束} 时超出范围 for 循环。因此,它不会增加以作为对重复生成的正确检查。理想情况下,您应该使用 std :: set 并继续插入其中。不允许重复,您可以避免很多麻烦。

更多关于使用 rand() srand()和随机数生成的信息:

来自comp.lang.c FAQ:

  

[...]许多随机数发生器的低阶位令人沮丧地非随机

如果您想将您的randome数字保持在

范围内
[0, 1, ... N - 1]

与简单的 rand()%N (如链接中所建议的)相比,更好的方法是使用以下内容:

(int)((double)rand() / ((double)RAND_MAX + 1) * N)

现在,如果你要运行你的程序,每次你将获得相同的10000多个随机DNA链。事实证明这是因为:

  

这是大多数伪随机数生成器(以及C库rand的定义属性)的特征,它们始终以相同的数字开始并经历相同的序列。

来自comp.lang.c的另一个常见问题解答

要在不同的运行中获得不同的链,请尝试以下方法:

#include <iostream>
#include <vector>
#include <fstream>
#include <sstream>
#include <ctime>
#include <cstdlib>
using namespace std;
    int main  ( int arg_count, char *arg_vec[] ) {

    // most pseudo-random number generators 
    // always start with the same number and 
    // go through the same sequence. 
    // coax it to do something different!
    srand((unsigned int)time((time_t *)NULL));

    // This is reference string
    string initVec("AAAA");    
    // the family
    string DNA("ACGT");

    for (unsigned i =0; i< 5; i++) {
       string newString;
       for(unsigned j=0; j<initVec.size(); j++) {
         int dnaNo = (int)((double)rand() / ((double)RAND_MAX + 1) * 4);
         char newBase = DNA[dnaNo];         
         newString += newBase;
       }
               // ideally push in a std::set 
               // for now keep displaying everything
         if (newString != initVec) {
               cout << "Run " << i << " : " << newString << endl; 
            }
         }
     return 0;
}

其他提示

你的算法是假的。无论你想做什么,你都没有这样做,因为那里没有一条评论,我无法确定你哪里出错了。

你的内心循环:

for each element of initVec (4)
    create a random element
    set sameCount to 0
    if random element == current element of initVec, set sameCount to 1
    if sameCount == 4, do something (pointless as this never happens)
    add random element to newString

再加上你的“newString”根本不是字符串,而是字符串向量。

所以,你的问题甚至不是使用 continue ,而是你的算法是FUBAR。

continue 不会跳过循环的的递增部分。它所做的就是直接转向它,跳过循环体的其余部分。

for(int i = 0; i < 10; i++)
{
  if(i == 3)
    continue;
  printf("%d ", i);
}

相当于:

int i = 0;
while(i < 10)
{
  if(i == 3)
    goto increment;
  printf("%d ", i);
increment:
  i++;
}

printf()中没有反斜杠,因为我无法弄清楚如何让文本编辑器让我输入一个。 :)

您是否意识到sameCount永远不会超过1?由于initVec.size()大于1,因此执行永远不会继续。

int sameCount = 0;
    //sameCount is 0
    if (newBase == oldBase) { // if it is true sameCount is 1
        sameCount++;
    }
    // sameCount is 1 or 0
    if (sameCount == initVec.size()) { //this expression is always false if initVec longer than 1
        continue;
    }

正如其他人已经说过很难找到你对这段代码的意图。你能告诉我们你的意思是“完全不同”吗?例如?

对于我现在想说的话,dirkgentlys的答案非常全面。

我建议您不要继续使用,大多数编码标准建议不要继续使用,因为它会使流量控制更难以遵循。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top