问题列表 - 第12832页

如何编写Java以允许SSE使用和边界检查消除(或其他高级优化)?

情况:

我正在优化LZF压缩算法的纯java实现,它涉及大量的byte []访问和基本的int数学,用于散列和比较.性能确实很重要,因为压缩的目标是降低I/O要求.我没有发布代码,因为它尚未清理,并且可能会进行大量重组.

问题:

  • 如何编写我的代码以允许它使用更快的SSE操作进行JIT编译到表单?
  • 我如何构造它,以便编译器可以轻松地消除数组边界检查?
  • 是否有关于特定数学运算的相对速度的广泛参考(等于正常加/减需要多少递增/递减,移位或对阵列访问的速度有多快)?
  • 我如何才能优化分支 - 最好是使用短体,或者一些长的条件语句,或者是嵌套条件的短条件语句?
  • 使用当前的1.6 JVM,在System.arraycopy击败复制循环之前必须复制多少个元素?

我已经做了什么:

在我因为过早优化而受到攻击之前:基本算法已经非常出色,但Java实现的速度不到等效C的2/3.我已经用System.arraycopy替换了复制循环,致力于优化循环并消除了un - 需要的操作.

我大量使用bit twiddling并将字节打包为整数,以实现性能,以及移位和屏蔽.

出于法律原因,我无法查看类似库中的实现,并且现有库具有过于严格的许可条款.

GOOD(已接受)答案的要求:

  • 不可接受的答案: "这个更快",没有解释为什么多少,为什么,或者没有用JIT编译器测试过.
  • 边界答案:在Hotspot 1.4之前没有经过任何测试
  • 基本答案:将提供一般规则和解释为什么它在编译器级别更快,大致更快
  • 好的答案:包括几个代码示例来演示
  • 优秀答案:拥有JRE 1.5和1.6的基准测试
  • 完美的答案:是由参与HotSpot编译器的人员完成的,可以完全解释或参考使用优化的条件,以及通常更快的速度.可能包含由HotSpot生成的java代码和示例汇编代码.

另外:如果有人有详细说明Hotspot优化和分支性能的内容的链接,那么欢迎这些.我对字节码有足够的了解,网站分析字节码而不是源代码级别的性能会有所帮助.

(编辑)局部答案:界限 - 检查消除:

这是从提供的HotSpot内部维基链接获取的:https://wikis.oracle.com/display/HotSpotInternals/RangeCheckElimination

HotSpot将消除所有for循环中的边界检查,具有以下条件:

  • 数组是循环不变的(不在循环中重新分配)
  • 索引变量有一个恒定的步幅(增量/减少恒定量,如果可能的话只在一个点)
  • 数组由变量的线性函数索引.

例: int val = array[index*2 + 5]

要么: int val = array[index+9]

不: int val = array[Math.min(var,index)+7]


早期版本的代码:

这是一个示例版本.不要窃取它,因为它是H2数据库项目的未发布版本的代码.最终版本将是开源的.这是对代码的优化:H2 CompressLZF代码

从逻辑上讲,这与开发版本相同,但是它使用for(...)循环来逐步执行输入,并使用if/else循环来实现文字和反向引用模式之间的不同逻辑.它减少了阵列访问和模式之间的检查.

public int compressNewer(final byte[] in, final int inLen, final byte[] out, int …
Run Code Online (Sandbox Code Playgroud)

java optimization performance jvm-hotspot bounds-check-elimination

40
推荐指数
2
解决办法
1万
查看次数

为什么start_routine for pthread_create返回void*并取无效*

pthread_create看起来像这样的函数头:

int pthread_create(pthread_t * thread, 
                   const pthread_attr_t * attr,
                   void * (*start_routine)(void *), 
                   void *arg);
Run Code Online (Sandbox Code Playgroud)

我理解这一切除了函数指针start_routine的形式void* (*fpointer) (void*),这意味着它接受一个void指针并返回一个void指针.

它所采用的void指针只是一种将参数传递给start_routine的方法,我得到了那个部分,但是我不明白为什么函数返回一个void指针?什么代码甚至会注意到void指针?

c posix pthreads

26
推荐指数
2
解决办法
1万
查看次数

SQL分层表中的Nulls与Guid.Empty

之情况:

我有一个带分层记录的文件夹表.行的ID是GUID类型.表上的ParentID存储父文件夹ID:

  • ID(Guid)
  • FolderName(varchar)
  • ParentID(Guid)

题:

插入顶级文件夹的最佳做法是什么?我应该将parentID列设为null,还是创建"顶级"记录(ID = Guid.Empty)并将该ID用于顶级文件夹?

c# sql

2
推荐指数
1
解决办法
3973
查看次数

制表间距

是否有相当于html中的控制台特殊字符'\ t'?

html xhtml

12
推荐指数
4
解决办法
6万
查看次数

让事情发生的机会C#

如何制作一个脚本,使一件事发生4/5次,另一件事发生1/5次

我需要它出现在此之后

private void Arrest()
{
    Ped Criminal = Player.GetTargetedPed();
    if (Exists(Criminal) && 
        (Player.Character.Position.DistanceTo(Criminal.Position) <= 10.0F))
    {
Run Code Online (Sandbox Code Playgroud)

.net c# scripting visual-studio

0
推荐指数
1
解决办法
254
查看次数

提高iPhone UITableView滚动性能的诀窍?

我有一个uitableview,在每个单元格中加载相当大的图像,并且单元格高度根据图像的大小而变化.滚动表现不错,但有时可能会生涩.

我在FieryRobot博客上找到了这些提示:

玻滚动与 - 的UITableView

更玻滚动与 - 的UITableView

有没有人有任何提高uitableview滚动性能的技巧?

iphone scroll uitableview uiimage ios

89
推荐指数
3
解决办法
5万
查看次数

如何确定字符串包含另一个字符串的位置?

有没有一种方法可以告诉像"foo bar Foo Bar one two three"这样的字符串,在哪个位置包含字符串"Foo",区分大小写?

iphone cocoa-touch objective-c

1
推荐指数
1
解决办法
125
查看次数

为什么Python的枚举速度如此之慢?

为什么"枚举"比"xrange + lst [i]"慢?


>>> from timeit import Timer
>>> lst = [1,2,3,0,1,2]*1000
>>> setup = 'from __main__ import lst'
>>> s1 = """
for i in range(len(lst)):
    elem = lst[i]
"""
>>> s2 = """
for i in xrange(len(lst)):
    elem = lst[i]
"""
>>> s3 = """
for i, v in enumerate(lst):
    elem = v
"""
>>> t1 = Timer(s1, setup); t2 = Timer(s2, setup); t3 = Timer(s3, setup)
>>> t1.timeit(3000), t2.timeit(3000), t3.timeit(3000)
(1.9263118636586494, 1.6119261665937992, 1.9606022553145719)
>>> t1.timeit(3000), t2.timeit(3000), t3.timeit(3000)
(1.93520258859715, 1.6145745478824836, 1.9529405971988041)

编辑:我记得为什么

for i, v in …
Run Code Online (Sandbox Code Playgroud)

python

6
推荐指数
2
解决办法
6111
查看次数

C中的指针实现细节

我想知道违反我在下面列出的假设的架构.此外,我想知道所有架构的假设是否都是错误的(也就是说,如果它们中的任何一个完全错误的话).

  1. sizeof(int*)== sizeof(char*)== sizeof(void*)== sizeof(func_ptr*)

  2. 无论指向哪种数据类型,给定体系结构的所有指针的内存中表示都是相同的.

  3. 指针的内存中表示与与体系结构相同的位长的整数相同.

  4. 指针数据类型的乘法和除法仅被编译器禁止.注意:是的,我知道这是荒谬的.我的意思是 - 是否有硬件支持禁止这种不正确的用法?

  5. 所有指针值都可以转换为单个整数.换句话说,哪些架构仍然使用分段和偏移?

  6. 递增指针相当于添加sizeof(the pointed data type)指针存储的内存地址.如果pint32*p+1则等于4字节后的内存地址p.

我最习惯在连续的虚拟内存空间中使用指针.对于这种用法,我通常可以将它们视为数字线上的地址.请参阅堆栈溢出问题指针比较.

c pointers sizeof virtual-memory

16
推荐指数
4
解决办法
5104
查看次数

有人可以滥用LINQ并解决这个钱难题吗?

为了它的乐趣,我想看到有人使用和滥用LINQ来解决这个钱的问题.我真的不知道你会怎么做 - 我想填充一些然后选择它.

如果给出一定数量的硬币并将所有硬币的总金额加在一起:显示每种可能的硬币组合.硬币是四分之一(.25),尺寸(.10)镍(.05)和便士(.01)

包括选项,以便硬币类型可以为零,或者每个硬币必须至少有1个.

示例问题:如果我有19个硬币并且硬币加起来为1.56美元并且每种类型的硬币必须至少有1个.

答案是:

1个季度,9个尺寸,8个镍,1个便士

2个宿舍,5个角,11个镍,1个便士

2个季度,9个尺寸,2个镍,6个便士

3个宿舍,1个角,14个镍,1个便士

3个宿舍,5个角,5个镍,6个便士

4个宿舍,1个角钢,8个镍币,6个便士

5个季度,1个尺寸,2个镍,11个便士

如果我们允许零投注,我们允许额外获得0个季度,13个角钱,5个镍币,1个便士

下面是一些使用强力方法解决问题的示例C#代码.不要费心改进样本,让我们看看使用Linq的解决方案.//如果可能的话,尽量不要使用任何regualar c#循环代码.

private void SolveCoinProblem(int totalNumberOfCoins, double totalAmount, int minimumNumberOfEachCoin)
    {
        int foundCount = 0;
        long numberOfTries = 0;
        Console.WriteLine(String.Format("Solving Coin Problem:TotalNumberOfCoins={0}TotalAmount={1}MinimumNumberOfEachCoin{2}", totalNumberOfCoins, totalAmount, minimumNumberOfEachCoin));
        for (int totalQuarters = minimumNumberOfEachCoin; totalQuarters < totalNumberOfCoins; totalQuarters++)
        {
            for (int totalDimes = minimumNumberOfEachCoin; totalDimes < totalNumberOfCoins; totalDimes++)
            {
                for (int totalNickels = minimumNumberOfEachCoin; totalNickels < totalNumberOfCoins; totalNickels++)
                {
                    for (int totalPennies = minimumNumberOfEachCoin; totalPennies < totalNumberOfCoins; totalPennies++)
                    { …
Run Code Online (Sandbox Code Playgroud)

c# linq math

10
推荐指数
1
解决办法
875
查看次数