Delphi中嵌套for循环的替代方法
我遇到了以下(概念上非常简单)问题,我想编写代码来解决这个问题,但我很挣扎。假设我们有两行等长,k。每行的每个单元格可以是0或1Delphi中嵌套for循环的替代方法,delphi,Delphi,我遇到了以下(概念上非常简单)问题,我想编写代码来解决这个问题,但我很挣扎。假设我们有两行等长,k。每行的每个单元格可以是0或1 例如,考虑下面的行对,k=5:01011, 00110</p> 现在,如果两行可以在每个单元格中自由交换值,那么将有2^5个可能的行对组合(其中一些可能不是唯一的)。例如,我们可以从上述数据中将00010111作为一个可能的行对。我想用Delphi编写代码,列出所有可能的行对。使用一组嵌套的for循环就很容易做到这一点。然而,如果k的值只在运行时才知道,我不确定如何使
例如,考虑下面的行对,k=5:01011, 00110</p> 现在,如果两行可以在每个单元格中自由交换值,那么将有2^5个可能的行对组合(其中一些可能不是唯一的)。例如,我们可以从上述数据中将00010111作为一个可能的行对。我想用Delphi编写代码,列出所有可能的行对。使用一组嵌套的for循环就很容易做到这一点。然而,如果k的值只在运行时才知道,我不确定如何使用这种方法,因为我不知道需要多少索引变量。我也看不出case语句有什么帮助,因为我不知道k的值
我希望有一种替代嵌套for循环的方法,但任何想法都将受到欢迎。谢谢。给定两个长度为k的向量A和B,我们可以通过从A或B中选择元素来生成一对新的向量A1和B1。让我们从A或B中选择的决定由同样长度为k的位向量S决定。对于[0..k]中的i,当Si为0时,将Ai存储在A1i中,将Bi存储在B1i中。如果Si为1,则反之亦然 我们可以在Delphi中使用如下函数定义:procedure GeneratePair(const A, B: string; S: Cardinal; out A1, B1: string);
var
k: Cardinal;
i: Cardinal;
begin
Assert(Length(A) = Length(B));
k := Length(A);
Assert(k <= 32);
SetLength(A1, k);
SetLength(B1, k);
for i := 1 to k do
if (S and (1 shl Pred(i))) = 0 then begin
A1[i] := A[i];
B1[i] := B[i];
end else begin
A1[i] := B[i];
B1[i] := A[i];
end;
end;
这有效地使用了一组嵌套循环。外部循环是从0到31的循环。内部循环是从1到
k
的函数内部循环。正如您所见,我们不需要事先知道k的值。现在,多亏了Rob,我理解了这个问题,我提供了以下递归解决方案:
{$APPTYPE CONSOLE}
procedure Swap(var A, B: Char);
var
temp: Char;
begin
temp := A;
A := B;
B := temp;
end;
procedure Generate(const A, B: string; Index: Integer);
var
A1, B1: string;
begin
Assert(Length(A)=Length(B));
inc(Index);
if Index>Length(A) then // termination
Writeln(A, ', ', B)
else
begin // recurse
// no swap
Generate(A, B, Index);
//swap
A1 := A;
B1 := B;
Swap(A1[Index], B1[Index]);
Generate(A1, B1, Index);
end;
end;
begin
Generate('01011', '00110', 0);
Readln;
end.
我不明白你想做什么-一些代码可以帮助我理解。你能展示你的代码在“固定”的
k
下工作吗?在运行时之前不知道k
根本不是问题,只要行的长度相等。你能发布到目前为止你尝试过的、你有困难的内容吗?(问代码的问题至少应该包括你自己努力寻找解决方案。)这听起来像是一个计算机科学问题。我假设这两行是“测试集”的一部分,不是吗。对不起,我做得有点过早。让我再多做一点,然后再发布一次问题。谢谢你的时间。
{$APPTYPE CONSOLE}
procedure Swap(var A, B: Char);
var
temp: Char;
begin
temp := A;
A := B;
B := temp;
end;
procedure Generate(const A, B: string; Index: Integer);
var
A1, B1: string;
begin
Assert(Length(A)=Length(B));
inc(Index);
if Index>Length(A) then // termination
Writeln(A, ', ', B)
else
begin // recurse
// no swap
Generate(A, B, Index);
//swap
A1 := A;
B1 := B;
Swap(A1[Index], B1[Index]);
Generate(A1, B1, Index);
end;
end;
begin
Generate('01011', '00110', 0);
Readln;
end.