【问题标题】:Making only the first letter of a word uppercase仅将单词的第一个字母变为大写
【发布时间】:2013-11-11 00:26:32
【问题描述】:

我有一种方法可以将句子中单词的所有首字母转换为大写。

public static String toTitleCase(String s)
{
    String result = "";
    String[] words = s.split(" ");

    for (int i = 0; i < words.length; i++) 
    {
        result += words[i].replace(words[i].charAt(0)+"", Character.toUpperCase(words[i].charAt(0))+"") + " ";
    }

    return result;
}

问题在于该方法将与第一个字母相同的单词中的其他字母转换为大写。例如,字符串 title 输出为 TiTle

对于输入this is a title,这将成为输出This Is A TiTle

我尝试了很多东西。一个嵌套循环,检查每个单词中的每个字母,如果有重复出现,则忽略第二个。我使用了计数器、布尔值等。没有任何效果,但我一直得到相同的结果。

我能做什么?我只想要大写的第一个字母。

【问题讨论】:

    标签: java string uppercase


    【解决方案1】:

    不要使用replace() 方法,而是尝试replaceFirst()

    result += words[i].replaceFirst(words[i].charAt(0)+"", Character.toUpperCase(words[i].charAt(0))+"") + " ";
    

    将输出:

    This Is A Title 
    

    【讨论】:

      【解决方案2】:

      问题是您正在使用replace 方法替换所有出现的描述字符。要解决此问题,您可以

      • 改用replaceFirst
        1. 取第一个字母,
        2. 创建大写版本
        3. 将它与其余的字符串连接起来,这可以通过substring 方法的一点帮助来创建。
      • 由于您使用的是使用正则表达式的replace(String, String),因此您可以在要替换的字符之前添加^,例如replace("^a","A")^ 表示输入的开始,因此它只会替换放置在输入开始之后的a

      我可能会使用第二种方法。


      目前在每个循环中,您的代码都会创建新的StringBuilder,其中存储在resultappend 中的新词给它,并重新分配result 的输出来自toString()
      这是感染性方法。相反,您应该在循环之前创建 StringBuilder 来代表您的结果,并在循环内创建 append 新词,在循环结束后,您可以使用 toString() 方法获取其字符串版本。

      【讨论】:

        【解决方案3】:

        做一些 Regex-Magic 可以简化你的任务:

        public static void main(String[] args) {
          final String test = "this is a Test";
        
          final StringBuffer buffer = new StringBuffer(test);
          final Pattern patter = Pattern.compile("\\b(\\p{javaLowerCase})");
          final Matcher matcher = patter.matcher(buffer);
          while (matcher.find()) {
            buffer.replace(matcher.start(), matcher.end(), matcher.group().toUpperCase());
          }
        
          System.out.println(buffer);
        }
        

        表达式\\b(\\p{javaLowerCase}) 匹配“单词的开头后跟一个小写字母”,而matcher.group() 等于匹配部分中 () 内的内容。示例:在“t”上应用“test”匹配,因此 start 为 0,end 为 1,group 为“t”。这甚至可以轻松遍历大量文本并替换所有需要替换的字母。

        另外:使用 StringBuffer(或类似的)进行字符串操作总是一个好主意,因为 Java 中的每个字符串都是唯一的。也就是说,如果您执行result += stringPart 之类的操作,您实际上会在每次调用它时创建一个新字符串(等于 result + stringPart)。因此,如果您使用 10 个部分执行此操作,最终您将在内存中至少有 10 个不同的字符串,而您只需要一个,即最后一个。

        StringBuffer 改为使用 char[] 之类的东西来确保如果您只更改单个字符,则不需要分配额外的内存。

        请注意,模式只需要编译一次,因此您可以将其作为类变量保存在某处。

        【讨论】:

          猜你喜欢
          • 2023-04-04
          • 1970-01-01
          • 2020-10-06
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2017-06-20
          • 1970-01-01
          相关资源
          最近更新 更多