string - 没有引用计数的交换字符串
问题描述
在 QuickSort 中,很多时间都花在了 swap 上temp:=var[i]; var[i]:=var[j]; var[j]:=temp
。当变量为整数时,我为大型随机数组计时 140 毫秒。当变量为字符串时,时间为 750 毫秒。在我看来,大部分差异是由于需要更新所有三个作业中的引用计数造成的。但这有必要吗?毕竟,var[i] 和 var[j] 的引用计数在这三个赋值之前和之后是相同的。下面的代码会破坏东西吗?(不是说它解决了速度问题,而是出于兴趣):
// P : Pstring;
move(values[i],P,sizeOf(Pstring));
move(values[j],values[i],sizeOf(Pstring));
move(P,values[i],sizeOf(Pstring));
没有临时变量。只有两个指向字符串的指针被互换。如果这没问题,是否有一个 Delphi 函数来交换 2 个指针?
解决方案
您提出的是一个众所周知且有效的优化。与其调用Move
函数,不如使用强制类型转换执行直接赋值以避免生成引用计数代码。
var
temp: Pointer;
....
temp := Pointer(var[i]);
Pointer(var[i]) := Pointer(var[j]);
Pointer(var[j]) := temp;
为了使其工作,您需要确信在交换过程中不会引发异常。有效内存的简单分配不会导致异常,因此可以轻松消除这种担忧。
推荐阅读
- php - 未捕获的类型错误:参数 2 传递给 Symfony\Component\EventDispatcher\EventDispatcher // Contao 4.7 & Symfony
- php - preg_match PHP 注释不包括引号
- apache-kafka - 启动时出现异常:NoSuchMethodException:org.springframework.kafka.core.KafkaTemplate。
() - java - 单选按钮的垂直滚动条
- php - 为什么我可以在这个 HTML 表中打印这个索引数组的值?
- haskell - splitOn 的内存占用?
- java - Firebase Android:获取存储在用户 ID 中的数据,然后获取随机 Push().getKey() 值
- java - 重新声明/重新定义 Java 变量循环
- r - 如何计算 R 曲线下面积的 Sobol 灵敏度?
- reactjs - 在 Jest 中测试无状态子组件中的父方法