【问题标题】:How to use stringBuilder如何使用字符串生成器
【发布时间】:2020-03-11 03:00:14
【问题描述】:

我有一个功能和技术负责人审查代码并说: 为什么这个 if 语句?这基本上是相同的消息。如果要自定义,请使用带有类型的字符串生成器。 怎么改,谁能帮帮我?

private Optional<String> validatePrimaryPath(SalesChannelType salesChannelCode, List<String> primaryPathList) {

  if (CollectionUtils.isEmpty(primaryPathList)) {
    if (salesChannelCode.equals(SalesChannelType.HEB_TO_YOU)) {
      return Optional.of("Customer Hierarchy is mandatory field for HebToYou.");
    } else {
      return Optional.of("Customer Hierarchy is mandatory field.");
    }
  }

  return Optional.empty();
}

【问题讨论】:

  • 我不会为此使用StringBuilder - 还是我遗漏了什么?
  • 我更关心原始类型。我也不会在这里使用StringBuilder
  • 我不明白为什么要在这里使用stringBuilder以及如何使用它。
  • 我同意@Scary Wombat。您可以使用单个 Optional.of 并通过三元运算符有条件地附加“for HebToYou”。只是一个想法......

标签: java string optional stringbuilder stringbuffer


【解决方案1】:

指定两个字符串文字意味着没有运行时开销。当所有参数都是编译时常量时,您可以使用字符串连接来实现相同的目的。相反,使用StringBuilder 总是意味着运行时操作。您可以在this answer 中阅读更多关于“StringBuilder 优于 + 的神话”。

您通常可以降低代码的语法复杂度:

private Optional<String> validatePrimaryPath(
    SalesChannelType salesChannelCode, List<String> primaryPathList) {

    final String prefix = "Customer Hierarchy is mandatory field";
    final String general = prefix + ".", forHebToYou = prefix + " for HebToYou.";

    return Optional.of(
            salesChannelCode.equals(SalesChannelType.HEB_TO_YOU)? forHebToYou: general)
        .filter(s -> CollectionUtils.isEmpty(primaryPathList));
}

这强调您正在做同样的事情,只是数据略有不同,并使用Optional 的语义而不是if 语句。如果您决定将实际字符串外部化,则实际代码不需要更改。

请注意,如果SalesChannelTypeenum,则不需要equals,则可以使用salesChannelCode == SalesChannelType.HEB_TO_YOU

【讨论】:

    【解决方案2】:

    为防止多次写入相同的(部分)字符串文字,您可以:

    • 对公共部分使用常量:

      if (CollectionUtils.isEmpty(primaryPathList)) {
          final String COMMON = "Customer Hierarchy is mandatory field";
          if (salesChannelCode.equals(SalesChannelType.HEB_TO_YOU)) {
              return Optional.of(COMMON + " for HebToYou.");
          } else {
              return Optional.of(COMMON + ".");
          }
      }
      
    • 使用StringBuilder构建字符串:

      if (CollectionUtils.isEmpty(primaryPathList)) {
          StringBuilder buf = new StringBuilder("Customer Hierarchy is mandatory field");
          if (salesChannelCode.equals(SalesChannelType.HEB_TO_YOU)) {
              buf.append(" for HebToYou");
          }
          return Optional.of(buf.append('.').toString());
      }
      

    就个人而言,我会将代码保留在问题中,特别是如果您可能需要支持文本的非英文版本,因为在其他语言中,额外的文本可能不会出现在那里。

    【讨论】:

    • 即使不使用编译时常量,我也不会使用StringBuilder,因为它会使代码复杂化而没有任何好处。在 Java 8 之前的所有 Java 版本中,使用 + 时无论如何都会得到此代码,而从 Java 9 开始,使用 + 时会变得更好(如 here 所讨论的)。但我喜欢在第二个变体中没有多余的Optional.of 调用。你甚至可以simplify the construct to a single statement...
    【解决方案3】:

    首先,不要使用原始类型。其次,我不同意使用StringBuilder 构建消息是一种改进;但是,既然那是您想要的,我将向您展示可能的意图。类似的,

    private Optional<String> validatePrimaryPath(SalesChannelType salesChannelCode, 
                    List<String> primaryPathList) {
        if (CollectionUtils.isEmpty(primaryPathList)) {
            StringBuilder sb = new StringBuilder(
                        "Customer Hierarchy is mandatory field");
            if (salesChannelCode.equals(SalesChannelType.HEB_TO_YOU)) {
                sb.append(" for HebToYou");
            }
            sb.append(".");
            return Optional.of(sb.toString());
        }
    
        return Optional.empty();
    }
    

    请注意,当您编写 OptionalList 而不指定类型时,我已指定该方法返回 Optional&lt;String&gt; 并采用 List&lt;String&gt;,那么您使用的是原始类型。

    【讨论】:

      【解决方案4】:

      就个人而言,我认为您的代码还可以,但如果您仍想使用StringBuilder,我有一个建议

      private Optional validatePrimaryPath(SalesChannelType salesChannelCode, List primaryPathList) {
          if (CollectionUtils.isEmpty(primaryPathList)) {
              StringBuilder sb = new StringBuilder("Customer Hierarchy is mandatory field.");
              if (salesChannelCode.equals(SalesChannelType.HEB_TO_YOU)) {
                  sb.insert(sb.length()-1, " for HebToYou");
              }
              return Optional.of(sb.toString());
          }
          return Optional.empty();
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2022-11-24
        • 1970-01-01
        • 2015-04-03
        • 1970-01-01
        • 2011-07-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多