java字符串置换_关于java:字符串置换…逻辑错误?

我正在尝试生成给定字符串的所有排列。

我使用的逻辑

suppose string =abcd

1) then i fix 'a'(and similarly each character.. first iteration - abcd, second-bacd, third-cabd.....)at first position in the first loop..

2) then generate strings by moving the second character ,i.e, 'b'

at all the places.. like abcd,acbd,acdb...

3) then i replace the 3rd( 4th ,5th and so on ) character with the

second charcter and repeat the second step again

4) i change abcd to bacd( n so for each character) and repeat steps

2,3...

现在不应该生成所有可能的组合..而且我也使用树集删除重复的条目...

但是不知何故,它产生的排列比实际少。例如,对于4个字符,仅20个排列...

这是相同的代码。

import java.util.*;

public class practice4 {

public static void main(String[] args) {

TreeSet t = new TreeSet();

String arr[] = new String[100];

int z = -1;

StringBuffer s5 = new StringBuffer("abcde");

for (int i = 0; i <= s5.length() - 1; i++) {

char ch = s5.charAt(0);

s5.setCharAt(0, s5.charAt(i));

s5.setCharAt(i, ch);

StringBuffer s3 = new StringBuffer(s5);

for (int j = 1; j <= s3.length() - 1; j++) {

StringBuffer s2 = new StringBuffer(s3);

// System.out.println(s2);

z++;

arr[z] = s2.toString();

for (int k = 1; k < s3.length() - 1; k++) {

char ch2 = s2.charAt(k);

s2.setCharAt(k, s2.charAt(k + 1));

s2.setCharAt(k + 1, ch2);

// System.out.println(s2);

z++;

arr[z] = s2.toString();

}

if (j >= s3.length() - 1)

break;

char ch3 = s3.charAt(1);

s3.setCharAt(1, s3.charAt(j + 1));

s3.setCharAt(j + 1, ch3);

}

System.out.println("dooone");

System.out.println(z);

for (int x = 0; x <= z; x++) {

t.add(arr[x]);

}

}

System.out.println(t.size());

Iterator i55 = t.iterator();

while (i55.hasNext()) {

System.out.println(i55.next());

}

}

}

我没有完全按照您的解释进行操作,但是仅通过查看您的代码具有3个嵌套循环这一事实,我就可以知道它对于大于3的字符串长度无效。一种更好的生成置换而不重复的方法是尝试放置每个 位置1的字符,并针对每种可能性,递归调用例程以查找剩余字符的所有排列的列表。 然后,您只需将每个这样的子置换附加到当前的第一个字符即可。

这篇文章中对所需的算法有很好的解释:stackoverflow.com/questions/756055/

@j_random_hacker ..是的,它不能使用3个或更多字符。.实际上它只能使用3个字符。但是此逻辑应生成所有组合,因为每个字符都在每个可能的位置...那么我不明白为什么它 不会..pls帮助,如果你可以或者那么我将不得不尝试n递归地做它...

您的3个嵌套循环可为长度为n的输入字符串最多生成n ^ 3个字符串。但是,排列的数量要大得多(n!),因此对于较大的n,结果集必须是部分的。

此外,关于逻辑应该生成所有排列的论点是不正确的,因为每个字符都在每个可能的位置。每个元素访问所有职位的事实并不意味着访问了所有可能的安排。例如,对于n = 3:

123

213

321

312

所有项目都出现在所有位置,但是列表仍然缺少序列132和231。

如果可以接受递归,请考虑以下解决方案:

public static Collection permutations(String s) {

ArrayList l = new ArrayList();

permutations(s.toCharArray(), 0, l);

return l;

}

private static void permutations(char[] chars, int i, ArrayList l) {

if (i == chars.length) {

l.add(new String(chars));

return;

}

for (int j = i; j < chars.length; j++) {

swap(chars, i, j);

permutations(chars, i + 1, l);

swap(chars, i, j);

}

}

private static void swap(char[] chars, int i, int j) {

char tmp = chars[i];

chars[i] = chars[j];

chars[j] = tmp;

}

该算法背后的归纳思想是,置换集是长度为n-1的所有置换的并集,其结果是选择第一个字符并以尾部递归地继续。假设输入字符串没有重复的字符,则此联合是不相交的,因此我们不必处理重复项。

非递归解决方案:

private static Collection permutations2(String str) {

ArrayList listNew = new ArrayList();

ArrayList listPrev = new ArrayList();

char chr = str.charAt(0);

listPrev.add("" + chr);

for (int i = 1; i < str.length(); i++) {

chr = str.charAt(i);

for (String s : listPrev) {

for (int idx = 0; idx <= s.length(); idx++) {

String perm = s.substring(0, idx) + chr + s.substring(idx);

listNew.add(perm);

}

}

listPrev = listNew;

listNew = new ArrayList();

}

return listPrev;

}

想法是,在第i阶段,我们根据前一阶段生成的长度i-1的所有排列生成长度i的所有排列。这是通过在长度为i-1的每个排列的所有可能位置插入新字符来完成的。假设原始字符串具有唯一字符,此解决方案还可以保证结果的唯一性。

感谢您浏览代码并指出错误。

但是我将不尝试解决方案,而是尝试提出另一种可行的算法:)

您可以查看以下任何帖子以寻求帮助:

要么

生成给定字符串的所有排列

谢谢,但是不谢谢..请回答你是否可以帮助错误的逻辑

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值