如何反转字符串中的所有单词,而不改变符号位置?

huangapple go评论85阅读模式
英文:

How to reverse all the words in a string, without changing symbol position?

问题

public void reverseWordInMyString(String str) {
String[] words = str.split(" ");
String reversedString = "";

for (int i = 0; i < words.length; i++) {

    String word = words[i];
    String reverseWord = "";

    for (int j = word.length()-1; j >= 0; j--) {

        reverseWord = reverseWord + word.charAt(j);
    }

    reversedString = reversedString + reverseWord + " ";
}
System.out.println(reversedString);

}

英文:

i have to write a program which will reverse all words in a string, but all symbols should stay on previous position for example: "a1bcd efg!h" => "d1cba hgf!e". I wrote a simple program which can reverse all words/symbols, but I have no idea how to make it like in example

public void reverseWordInMyString(String str) {
    String[] words = str.split(&quot; &quot;);
    String reversedString = &quot;&quot;;

    for (int i = 0; i &lt; words.length; i++) {

        String word = words[i];
        String reverseWord = &quot;&quot;;

        for (int j = word.length()-1; j &gt;= 0; j--) {

            reverseWord = reverseWord + word.charAt(j);
        }

        reversedString = reversedString + reverseWord + &quot; &quot;;
    }
    System.out.println(reversedString);
}

答案1

得分: 2

这是一个良好的开始。问题只是有点棘手。

你当前的方法使用了一个单一的“累加器”,它从字符串的末尾开始向后移动:for (int j =...) 中的 j

你需要两个累加器来完成这个作业任务:一个从前向后递增的累加器(因此是 for (int i = 0; i < word.length(); i++)),和一个从末尾开始递减的累加器,但不是连续的。

思路是:当你向前移动时,你检查在位置 i 找到的字符。然后,根据条件使用 if,因为问题要求你根据条件执行不同的操作:

  • 如果在 i 处的字符是特殊字符,只需将其添加。
  • 否则,添加字符串中我们尚未添加的最后一个非特殊字符。

if 情况很简单。而 else 情况不是。这就是你第二个累加器的用处:这个累加器将跟踪你在字符串中的位置,从末尾开始。这是一个循环中的循环。你需要:

重复以下算法:

  • 如果位于 j 处的字符(从末尾到开头)是特殊字符,则递减 j,并重新启动此算法。
  • 否则,那就是“我们尚未添加的最后一个非特殊字符”,因此添加该字符,递减 j,并退出此算法。

上述操作可以使用 while 或 do/while 循环来完成。它将嵌套在你的 for 循环内部。

祝你好运!

注意:这不是唯一的方法。例如,你也可以从输入中消除所有特殊字符,对每个单词进行基本的反转,这比你现在的方法要简单得多,因为字符串现在有一个 .reverse() 方法,然后,在所有这些操作之后,逐个字符遍历你的原始输入,并对每个特殊字符在输出字符串中的位置插入该字符。这也可以工作。无论哪种策略你更喜欢!

英文:

It's a good start. The question is just that tricky.

Your current approach uses a single 'accumulator' which starts at the end of the string and moves back to the start: The j in for (int j =...).

You'll need two accumulators to complete this homework assignment: One going from the front to the back, which steadily increments (so, that'll be for (int i = 0; i &lt; word.length(); i++)), and one which starts at the end and decrements, but not steadily.

The idea is: As you go forward, you inspect the character you find at position i. Then, you use an if, as the question asks you to do different things depending on a condition:

  • if the character at i is a special character, just add it.
  • else, add the last non-special character in the string we haven't yet added.

the if case is trivial. The else case is not. That's where your second accumulator comes in: This one will track where you're at in the string, from the end. This is a loop-in-loop. What you'll need to:

repeat the following algorithm:

  • If the character at 'j' (which goes from end to start) is a special character, decrement j, and restart this algorithm
  • Otherwise, that's the 'last non-special character we havent yet added', so add that, decrement j, and escape this algorithm.

The above can be done with, for example, a while or do/while loop. It'll be inside your for loop.

Good luck!

NB: This isn't the only way to do it. For example, you could also eliminate all special characters from the input, do a basic reverse on every word inside, which is a lot simpler than what you have now, as string has a .reverse() method these days, and then, after all that, go through your original input character by character, and for each special character you find, insert that character at that position in your output string. That works too. Whichever strategy you prefer!

答案2

得分: 1

根据www.geeksforgeeks.org提供的信息:

问题:

给定一个字符串,其中包含特殊字符和字母(从‘a’到‘z’和从‘A’到‘Z’),以一种不影响特殊字符的方式反转字符串。

解决方案:

  1. 创建一个临时字符数组,命名为temp[]。
  2. 将给定数组中的字母字符复制到temp[]中。
  3. 使用标准的字符串反转算法反转temp[]。
    现在在单个循环中遍历输入字符串和temp。每当输入字符串中有字母字符时,用temp[]的当前字符替换它。

算法:

1) 让输入字符串为 'str[]',字符串长度为 'n'
2) l = 0,r = n-1
3) 当 l 小于 r 时,执行以下操作
    a) 如果 str[l] 不是字母字符,则 l++
    b) 否则如果 str[r] 不是字母字符,则 r--
    c) 否则交换 str[l] 和 str[r]

Java 代码:

public static void main(String[] args){
    String s = "Thi!s is a sa5mpl?e sentence.";
    String[] words = s.split("\\s+");
    System.out.println("Result:" + reverse(s));
    //输出:sih!T si a el5pma?s ecnetnes.
}

public static String reverse(String input)
{
    String[] words = input.split("\\s+");
    String last_str = "";

    for(int j=0;j<words.length;j++){
        char[] str = words[j].toCharArray();
        int r = str.length - 1, l = 0;

        // 从两端遍历字符串直到 'l' 和 'r'
        while (l < r)
        {
            // 忽略特殊字符
            if (!Character.isAlphabetic(str[l]))
                l++;
            else if(!Character.isAlphabetic(str[r]))
                r--;

            // str[l] 和 str[r] 都不是特殊字符
            else
            {
                str[l] ^= str[r]; // 使用三重异或交换
                str[r] ^= str[l];
                str[l] ^= str[r];
                l++;
                r--;
            }
        }
        last_str = last_str + new String(str) + " ";
    }
    // 初始化左右指针

    return last_str;
}
英文:

according to www.geeksforgeeks.org

The Problem:

Given a string, that contains special character together with alphabets (‘a’ to ‘z’ and ‘A’ to ‘Z’), reverse the string in a way that special characters are not affected.

Solution:

  1. Create a temporary character array say temp[].
  2. Copy alphabetic characters from given array to temp[].
  3. Reverse temp[] using standard string reversal algorithm.
    Now traverse input string and temp in a single loop. Wherever there is alphabetic character is input string, replace it with current character of temp[].

Algorithm:

1) Let input string be &#39;str[]&#39; and length of string be &#39;n&#39;
2) l = 0, r = n-1
3) While l is smaller than r, do following
    a) If str[l] is not an alphabetic character, do l++
    b) Else If str[r] is not an alphabetic character, do r--
    c) Else swap str[l] and str[r]

Java Code:

	public static void main(String[] args){
		String s = &quot;Thi!s is a sa5mpl?e sentence.&quot;;
		String[] words = s.split(&quot;\\s+&quot;);
		System.out.println(&quot;Result:&quot; + reverse(s));
		//Output: sih!T si a el5pma?s ecnetnes.
	}

	public static String reverse(String input)
	{
		String[] words = input.split(&quot;\\s+&quot;);
		String last_str = &quot;&quot;;

		for(int j=0;j&lt;words.length;j++){
			char[] str = words[j].toCharArray();
			int r = str.length - 1, l = 0;

			// Traverse string from both ends until
			// &#39;l&#39; and &#39;r&#39;
			while (l &lt; r)
			{
				// Ignore special characters
				if (!Character.isAlphabetic(str[l]))
					l++;
				else if(!Character.isAlphabetic(str[r]))
					r--;

					// Both str[l] and str[r] are not spacial
				else
				{
					str[l] ^= str[r];//swap using triple XOR
					str[r] ^= str[l];
					str[l] ^= str[r];
					l++;
					r--;
				}
			}
			last_str = last_str + new String(str) + &quot; &quot;;
		}
		// Initialize left and right pointers

		return last_str;
	}

}

答案3

得分: 0

我会按照以下方式处理这个问题:

  1. 跟踪当前单词的起始位置(或者等效地,上一个非单词字符的位置)。这将随着我们的处理而更新。
  2. 扫描输入字符串。每当找到非单词字符(特殊字符或空格)时,输出当前单词的反转,然后是非单词字符。您可以通过从非单词字符之前的位置倒序索引到当前单词的起始位置来输出当前单词的反转。(请注意,当前单词可能为空;例如,连续两个特殊字符)。

对于输出区域,我建议使用 StringBuilder 而不是 String;这将更加高效。

在代码中,它可能看起来像这样(我已经更改了方法以返回结果而不是将其打印到控制台):

public String reverseWordInMyString(String str) {
    StringBuilder output = new StringBuilder(str.length()); // 初始化容量
    int curWordStart = 0;
    // 扫描输入字符串
    for (int i = 0; i < str.length(); i++) {
        char curLetter = str.charAt(i);
        if (!Character.isLetter(curLetter)) {
            // 当前单词已结束--以反序输出它
            for (int j = i - 1; j >= curWordStart; j--) {
                output.append(str.charAt(j));
            }
            // 输出当前字母
            output.append(curLetter);
            // 下一个当前单词从当前字母之后开始
            curWordStart = i + 1;
        }
    }
    // 最后一个当前单词(如果有的话)以字符串的结束而不是特殊字符结束,因此也将其(反转)添加到输出中
    for (int j = str.length() - 1; j >= curWordStart; j--) {
        output.append(str.charAt(j));
    }

    return output.toString();
}

希望这能帮助您理解代码的翻译。如果您有任何问题,请随时提问。

英文:

I would approach this as follows:

  1. Keep track of where the current word starts (or, equivalently, where the last non-word character was). This will be updated as we go along.
  2. Scan the input string. Every time a non-word character (special character or space) is found, output the reverse of the current word and then the non-word character. You can output the reverse of the current word by indexing backwards from just before the non-word character to the start of the current word. (Note that the current word might be empty; for example, two special characters in a row).

For the output area, I recommend a StringBuilder rather than a String; this will be more efficient.

In code, it might look something like this (where I've changed the method to return the result rather than print it to the console):

public String reverseWordInMyString(String str) {
    StringBuilder output = new StringBuilder(str.length()); // initialize full capacity
    int curWordStart = 0;
    // scan the input string
    for (int i = 0; i &lt; str.length(); i++) {
        char curLetter = str.charAt(i);
        if (!Character.isLetter(char)) {
            // the current word has ended--output it in reverse
            for (int j = i-1; j &gt;= curWordStart; j--) {
                output.append(str.charAt(j));
            }
            // output the current letter
            output.append(curLetter);
            // the next current word starts just after the current letter
            curWordStart = i + 1;
        }
    }
    // The last current word (if any) ends with the end of string,
    // not a special character, so add it (reversed) as well to output
    for (int j = str.length() - 1; j &gt;= curWordStart; j--) {
        output.append(str.charAt(j));
    }

    return output.toString();
}

huangapple
  • 本文由 发表于 2020年8月5日 20:04:28
  • 转载请务必保留本文链接:https://go.coder-hub.com/63264794.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定