SQL中StringBuilder的正确使用方法

2024-05-11

我刚刚在我的项目中发现了一些像这样的 sql 查询构建:

return (new StringBuilder("select id1, " + " id2 " + " from " + " table")).toString();

做这个StringBuilder实现其目标,即减少内存使用?

我对此表示怀疑,因为在构造函数中使用了“+”(字符串连接运算符)。这会占用与使用 String (如下面的代码)相同的内存量吗?我明白了,使用时有所不同StringBuilder.append().

return "select id1, " + " id2 " + " from " + " table";

两个语句的内存使用量是否相等?请澄清。

Edit:

BTW, 这不是我的代码。在一个旧项目中找到的。此外,查询并不像我的示例中的查询那么小。 :)


使用StringBuilder的目的,即减少内存。实现了吗?

一点都不。该代码没有使用StringBuilder正确。 (不过,我认为你错误地引用了它;肯定没有引用id2 and table?)

请注意,目标(通常)是减少内存churn而不是使用的总内存,以使垃圾收集器的工作变得更轻松。

这会占用与使用 String 相同的内存吗?

不,会导致more记忆搅动不仅仅是你引用的直接连接。 (直到/除非 JVM 优化器发现显式StringBuilder代码中是不必要的,如果可以的话,将其优化掉。)

如果该代码的作者想要使用StringBuilder(有支持的论据,但也有反对的;请参阅本答案末尾的注释),最好正确地执行(这里我假设实际上没有引号)id2 and table):

StringBuilder sb = new StringBuilder(some_appropriate_size);
sb.append("select id1, ");
sb.append(id2);
sb.append(" from ");
sb.append(table);
return sb.toString();

请注意,我已经列出了some_appropriate_size in the StringBuilder构造函数,以便它一开始就有足够的容量来容纳我们要附加的全部内容。如果您未指定,则使用的默认大小是16 个字符 http://docs.oracle.com/javase/6/docs/api/java/lang/StringBuilder.html#StringBuilder%28%29,通常太小,导致StringBuilder必须进行重新分配以使自身变得更大(IIRC,在 Sun/Oracle JDK 中,它会将自身加倍[或更多,如果它知道需要更多来满足特定的需求)append] 每次空间不足时)。

您可能听说过字符串连接will use a StringBuilder如果使用 Sun/Oracle 编译器进行编译,则在幕后。这是真的,它会使用一个StringBuilder为了整体的表达。但它将使用默认构造函数,这意味着在大多数情况下,它必须进行重新分配。不过,它更容易阅读。请注意,这是not真实的一个series的串联。例如,这使用一个StringBuilder:

return "prefix " + variable1 + " middle " + variable2 + " end";

大致可以翻译为:

StringBuilder tmp = new StringBuilder(); // Using default 16 character size
tmp.append("prefix ");
tmp.append(variable1);
tmp.append(" middle ");
tmp.append(variable2);
tmp.append(" end");
return tmp.toString();

所以没关系,尽管默认构造函数和随后的重新分配并不理想,但很可能它已经足够好了 - 并且串联是lot更具可读性。

但这仅适用于单个表达式。多种的StringBuilders 用于此目的:

String s;
s = "prefix ";
s += variable1;
s += " middle ";
s += variable2;
s += " end";
return s;

最终变成这样:

String s;
StringBuilder tmp;
s = "prefix ";
tmp = new StringBuilder();
tmp.append(s);
tmp.append(variable1);
s = tmp.toString();
tmp = new StringBuilder();
tmp.append(s);
tmp.append(" middle ");
s = tmp.toString();
tmp = new StringBuilder();
tmp.append(s);
tmp.append(variable2);
s = tmp.toString();
tmp = new StringBuilder();
tmp.append(s);
tmp.append(" end");
s = tmp.toString();
return s;

……这实在是太丑了。

但重要的是要记住,除了极少数情况外,没关系除非出现特定的性能问题,否则优先考虑可读性(这会增强可维护性)。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

SQL中StringBuilder的正确使用方法 的相关文章

随机推荐

  • MongoDB 查询返回空数组

    有一个基本的 Express 应用程序连接到几乎 0 5 GB 的 MongoDB 数据库 当我运行时 router get function req res next medical data find State CT function
  • 从 google Drive 自行下载 xlsx 文件

    所以 我正在尝试制作一个小脚本 它将使用谷歌驱动器API下载一个Excel文件 通过遵循谷歌API教程 我遇到了两个错误 无法读取未定义的 on 属性 和 请求的转换是不支持 这是代码 const fs require fs const r
  • 如何手动推断表达式的类型

    给定 Haskell 函数 head filter fst 现在的问题是如何手动 手动 找到类型 如果我让 Haskell 告诉我我得到的类型 head filter fst Bool b gt Bool b 但我想了解仅使用所用函数的签名
  • 无法在 SBT 中运行 Apache Spark 相关单元测试 - NoClassDefFoundError

    我有一个简单的单元测试 使用SparkContext 我可以在 IntelliJ Idea 中运行单元测试 没有任何问题 但是 当尝试从 SBT shell 运行相同的测试时 我收到以下错误 java lang NoClassDefFoun
  • 跟踪 C++ 中递归函数被调用的次数

    我正在尝试编写一个程序 该程序具有一个参数是字符串向量的函数 我想在该函数上使用递归 但每次调用该函数时 我想更改参数 例如 fun stringArray i 其中 i 是调用该函数的次数 因此 以更简单的方式 如下所示 但我需要跟踪函数
  • 用于裁剪和转置视频的 FFMPEG 命令放大后质量较差

    我正在尝试将尺寸通常为 960x720 的 mp4 视频转换为方形 480 480 视频 但它通常看起来被压扁 命令是 y i s vf crop 480 480 transpose d threads 5 metadata s v rot
  • Python 中最宽容的 HTML 解析器是什么?

    我有一些随机的 HTML 我使用 BeautifulSoup 来解析它 但在大多数情况下 gt 70 它会令人窒息 我尝试使用Beautiful soup 3 0 8和3 2 0 3 1 0以上有一些问题 但结果几乎相同 我可以从我的脑海中
  • 如何在UIWindow中添加视图?

    我想添加一个视图UIWindow与以下代码 AppDelegate delegate AppDelegate UIApplication sharedApplication delegate UIWindow window delegate
  • Javascript 连接 [重复]

    这个问题在这里已经有答案了 我在在线 javascript 测验中发现了以下代码片段 我无法理解这种串联在 JS 中是如何工作的 有人可以解释一下这是如何工作的吗 output foo output foo Javascript 尝试应用
  • swift:移动动画

    我在故事板中有 viewController 还有4个正方形 我想将我的方块放在视图中 首先我想显示两个正方形 如果我按下按钮 我希望我的红色 2 个方块向左移动 然后显示接下来的 2 个蓝色方块 就像这部动画 我需要创建一个scrollV
  • 为什么我的原生 C++ 代码在 Android 上运行速度比 Java 慢很多?

    我将 Java 代码的某些部分移植到 C 以加快 Android 上的计算速度 这是一个物理子例程 我发现本机代码的运行速度比 Java 代码慢几倍 我认为我的项目配置可能有问题 或者可能是数组处理有问题 所以我在 HelloAndroid
  • `class_eval` 字符串中的变量范围是什么?

    我在用class eval编写要在当前类的上下文中执行的代码 在下面的代码中 我想添加一个用于属性值更改的计数器 class Class def attr count attr name attr name attr name to s a
  • Exposé 布局算法

    我正在制作一些项目 其布局类似于 Mac OS X 在 Expos 中对窗口所做的操作 它适应项目的长宽比和可用区域的长宽比 基本上 可用区域分为行和列 每个单元格 行和列的交集 中放置一个项目 这些项目必须保持其纵横比 此处width h
  • Xcode 8.2.1 无法添加文件夹引用

    我的 Xcode 8 2 1 不允许我添加文件夹引用 我尝试过的 我右键单击名为 Unity 的文件夹 然后单击 将文件添加到项目 在选项下选中 创建文件夹引用 我的文件夹被添加为红色文件 而不是通常的蓝色文件夹 我尝试将文件的 类型 更改
  • MaterializeCSS select 不适用于 ng-repeat

    MaterializeCSS 选择重复选项 使用ng repeat 不管用 请帮忙 div class col s12 input field div
  • 无法在 Windows 7 机器中使用 OpenCV 2.4.3、Python 2.7 打开“.mp4”视频文件

    我目前正在进行一个涉及读取 mp4 视频文件的项目 我遇到的问题是它在Windows 7机器上使用Python 2 7 32位 OpenCV 2 4 3 cv2 pyd 代码片段如下 try video cv2 VideoCapture v
  • 无法使用 java 8 在 Windows 10 上安装 elasticsearch 5.1.1

    我正在尝试在安装了 java 8 111 的 Windows 10 笔记本电脑上安装 ElasticSearch 5 1 1 当我尝试安装 Elastic search 时触发错误 C Users 用户名 Downloads elastic
  • 如何通过id获取最近共享的AWS RDS快照?

    我在 AWS RDS 上有 2 个数据库 其中一个用于stage和一个用于production跨 2 个帐户 我正在尝试将数据复制到production to stage每 x 天 我的计划是复制最近的自动备份快照production并分享
  • ios6 中不再调用 viewDidUnload

    我刚刚安装了新版本的 Xcode ios 6 viewDidUnload 现已弃用 在苹果文档中 viewDidUnload 在 iOS 6 0 中已弃用 在内存不足的情况下不再清除视图 因此永远不会调用此方法 但许多应用程序正在使用此回调
  • SQL中StringBuilder的正确使用方法

    我刚刚在我的项目中发现了一些像这样的 sql 查询构建 return new StringBuilder select id1 id2 from table toString 做这个StringBuilder实现其目标 即减少内存使用 我对