string[,] urlArray = new string[,]
{
{"05", "02", "00", "1"},//起始位置
{"19", "04", "99","8"}//结束位置,分别与上面一一对应
};
我要产生出:
//第一重循环
xx05xxx02xx00x1
xx06xxx02xx00x1
...
xx19xxx02xx00x1
//第二重循环
xx05xxx03xx00x1
xx06xxx03xx00x1
xx07xxx03xx00x1
...
xx19xxx03xx00x1
...
xx19xxx04xx00x1
//第三重循环.....
xx19xxx04xx99x8这样的字符串。
{
{"05", "02", "00", "1"},//起始位置
{"19", "04", "99","8"}//结束位置,分别与上面一一对应
};
我要产生出:
//第一重循环
xx05xxx02xx00x1
xx06xxx02xx00x1
...
xx19xxx02xx00x1
//第二重循环
xx05xxx03xx00x1
xx06xxx03xx00x1
xx07xxx03xx00x1
...
xx19xxx03xx00x1
...
xx19xxx04xx00x1
//第三重循环.....
xx19xxx04xx99x8这样的字符串。
{
{"05", "02", "00", "1"},//起始位置
{"19", "04", "99","8"}//结束位置,分别与上面一一对应
};
public string[] BuildString()
{
int i1 = Convert.ToInt32(urlArray[0,0]);
int i2 = Convert.ToInt32(urlArray[1,0]);
int i3 = Convert.ToInt32(urlArray[0,1]);
int i4 = Convert.ToInt32(urlArray[1,1]);
int i5 = Convert.ToInt32(urlArray[0,2]);
int i6 = Convert.ToInt32(urlArray[1,2]);
int i7 = Convert.ToInt32(urlArray[0,3]);
int i8 = Convert.ToInt32(urlArray[1,3]);
string[] mm = new string[(i2-i1+1)*(i4-i3+1)*(i6-i5+1)*(i8-i7+1)];
long i9 = 0;
for(int j = i1;j<=i2;j++)
{
for(int k = i3;k<=i4 ;k++)
{
for(int l = i5;l<=i6;l++)
{
for(int m = i7;m<=i8;m++)
{
mm[i9] = j.ToString()+"xxx"+k.ToString()+"xxx"+l.ToString()+"xxx"+m.ToString()+"xxx";
i9++;
}
}
}
}
return mm;
}
string[,] urlArray = new string[,]
{
{"05", "02", "00", "1", "13", "0"},//起始位置
{"19", "04", "99", "8", "99", "9"}//结束位置,分别与上面一一对应
};
增加了两维,这样的算法就不具有通用性。
我的问题是:如何自动构建多种循环呢?
其作用是把template里面的第一个占位符@用从start到end之间的自然数填充,返回这个数组。然后就是递归了。string[] GetStrings( string template, int[] start, int[] end )
{
List<string> collection = new List<string>(); int[] _start = new List<int>( start ).RemoveAt(0);//把第一项从列表中去除,下同。其实可以用Stack,算了,为了简单。我只给出思想。
int[] _end = new List<int>( end ).RemoveAt(0); if ( start.Length == 0 )
return new string[] {};//返回空数组 foreach ( string str in GetStrings( start[0], end[0] ) )
{
collection.AddRange( GetStrings( str, _start, _end ) );
} return collection.ToArray();
}
先利用上面那个GetStrings把第一个占位符换掉:
换成:
xx1xxxxx@xxxx@xxxx@xx
xx2xxxxx@xxxx@xxxx@xx
xx3xxxxx@xxxx@xxxx@xx
……
xx8xxxxx@xxxx@xxxx@xx
的形式然后把每一个替换后的结果就作为模板传给自己
自己就会把每一种都扩展为:
xx1xxxxx1xxx@xxxx@xx
xx1xxxxx2xxx@xxxx@xx
xx1xxxxx3xxx@xxxx@xx
的形式。上面的只是伪代码,实际需要更多的优化和修改,例如直接返回容器而不是数组等。
foreach ( string str in GetStrings( template, start[0], end[0] ) )
可否将代码写全,麻烦你了,我搞了差不多两天了。
{ //获取每个字数填空字符x
string[] xNums = xs.Split(",".ToCharArray());
//新建一个数组,用于存储当前每个数字的当前值
int[] orinumbegin = new int[urlArray.Length/2];
int[] orinumend =new int[urlArray.Length/2];
int[] curnums = new int[urlArray.Length/2];
int[] lens = new int[urlArray.Length/2];
for(int i = 0; i < lens.Length; i++)
{
orinumbegin[i] = int.Parse(urlArray[0, i]);
orinumend[i] = int.Parse(urlArray[1, i]);
curnums[i] = int.Parse(urlArray[0, i]);
lens[i] = urlArray[1, i].Length;
} //有多少数字 int count=0;
while(true)
{
//对第一个值进行循环
for(int i = orinumbegin[0]; i <= orinumend[0]; i++)
{
StringBuilder sb = new StringBuilder(); //获取各个数字的当前的值
for(int j = 0; j < orinumbegin.Length; j++)
{
sb.Append(xNums[j]);
string s = curnums[j].ToString().PadLeft(lens[j], '0');
sb.Append(s);
count++;
}
Debug.WriteLine(sb.ToString());
curnums[0]++;
}
curnums[0] = orinumbegin[0];
for(int j = 1; j < curnums.Length; j++)
{
if (curnums[j] + 1 > orinumend[j]) //判断当前数字是否达到最大值
{
if (j == curnums.Length - 1) //判断是否是最后一个数字,就退出
{
Debug.WriteLine(count.ToString());
return;
}
else //如果不是最后一个数字,就将当前设为初始值,
{
curnums[j] = orinumbegin[j];
continue;
}
}
else //没有达到最大值就加一
{
curnums[j]++;
break;
}
}
}
}
调用方法
string[,] urlArray = new string[,]
{
{"05", "02", "00", "1"},//起始位置
{"19", "04", "99","8"}
};
string xs = "xx,xxx,xx,x";
PrintChar(urlArray, xs);
但是我知道楼主的那个字符串不仅仅是xxx吧,所以切分也挺费神的,不过用正则就……还是觉得思路有问题……
就是使用正则表达式,将链接切分,比如:http://www.domainname.com/download/20(05)(01)(02)/img/(001)/a(01).jpg等等,使用正则表达式将所有字符串分隔开来,然后就可以重组字符串出来了。