Js(+ Mootools) - 为什么我的脚本使用超过60%的处理器?

时间:2010-04-02 10:12:40

标签: javascript php mootools cpu-usage

在这个网站上 - LINK - 我需要使用3个横幅滚动条(2x垂直+ 1x水平)。我试图在flash中执行此操作,但随后每个Web浏览器都会关闭或暂停。现在我想用JS(我使用mootools)。所有数据都来自MySQL。这是完整的代码(即使你不知道mootools,你应该理解它)

global $wpdb;
$table = $wpdb->prefix.'part';
$sql = "SELECT * FROM $table";
$q = $wpdb->get_results($sql);
$g = 0;
if($wpdb->num_rows > 0)
{
?>
<script type="text/javascript">
window.addEvent('load', function(){
    var totall = 0;
    var totalr = 0;
    $$('#leftCont0 .contElement').each(function(el){
        var img = new Asset.image(el.getFirst('a').getFirst('img').get('src'));
        totall += img.height;
    });
    $$('#rightCont0 .contElement').each(function(el){
        var img = new Asset.image(el.getFirst('a').getFirst('img').get('src'));
        totalr += img.height;
    });

    $$('.leftCont').each(function(el){
        var h = parseInt(el.get('id').substr(8));
        el.setStyle('top', h * totall);
    });
    $$('.rightCont').each(function(el){
        var h = parseInt(el.get('id').substr(9));
        el.setStyle('top', h * totalr);
    });
    var total = new Array(totall, totalr);
    move.periodical(30, null, total);
});
function move(num, num2)
{
    var h = 0;
    var da = false;
    var target = null;
    $$('.leftCont').each(function(el){
        var act = el.getStyle('top');
        var n = parseInt(act)+1;
        el.setStyle('top', n+"px");
        if(el.getStyle('top') < h)
        {
            h = parseInt(el.getStyle('top'));
            alert(h);
        }
        if(parseInt(el.getStyle('top')) > 400)
        {
            da = true;
            target = el;
        }
    });
    if(da)
    {
        var n = h - num;
        target.setStyle('top', n+'px');
    }
    h = 0;
    da = false;
    $$('.rightCont').each(function(el){
        var act = el.getStyle('top');
        var n = parseInt(act)+1;
        el.setStyle('top', n+"px");
        if(el.getStyle('top') < h)
        {
            h = parseInt(el.getStyle('top'));
            alert(h);
        }
        if(parseInt(el.getStyle('top')) > 400)
        {
            da = true;
            target = el;
        }
    });
    if(da)
    {
        var n = h - num2;
        target.setStyle('top', n+'px');
    }
}
</script>
<?php 
$g = 0;
$l = 0;
$r = 0;
$leftContent = array();
$rightContent = array();
$leftHeight = 0;
$rightHeight = 0;
foreach($q as $q)
{
    if(($g % 2) == 0)
    {
        $leftContent[$l] = '<div class="contElement">
                <a href="'.$q->aurl.'"><img src="'.$q->imgurl.'" alt="Partner" /></a>
            </div>';
        $lHeight = getimagesize($q->imgurl);
        $leftHeight .= $lHeight[1];
        $l++;
    }
    else
    {
        $rightContent[$r] = '<div class="contElement">
                <a href="'.$q->aurl.'"><img src="'.$q->imgurl.'" alt="Partner" /></a>
            </div>';
        $rHeight = getimagesize($q->imgurl);
        $rightHeight .= $rHeight[1];
        $r++;
    }
    $g++;
}
$quantity = ceil(400 / $leftHeight) + 1;

for($i = 0; $i < $quantity; $i++)
{
    $str = "";
    for($j = 0; $j < sizeof($leftContent); $j++)
    {
        $str .= $leftContent[$j];
    }
    $leftContainer[$i] = '<div class="leftCont" id="leftCont'.$i.'">'.$str.'</div>';
}

$quantity = ceil(400 / $rightHeight) + 1;

for($i = 0; $i < $quantity; $i++)
{
    $str = "";
    for($j = 0; $j < sizeof($rightContent); $j++)
    {
        $str .= $rightContent[$j];
    }
    $rightContainer[$i] = '<div class="rightCont" id="rightCont'.$i.'">'.$str.'</div>';
}

?>
<div id="pcl">
<?php
for($i = 0; $i < sizeof($leftContainer); $i++)
{
    echo $leftContainer[$i];
}
?>
</div>
<div id="pcr">
<?php
for($i = 0; $i < sizeof($rightContainer); $i++)
{
    echo $rightContainer[$i];
}
?>  
</div>
<?php
}

2 个答案:

答案 0 :(得分:1)

具有两个move()循环的each()函数每30毫秒执行一次是很昂贵的。因为所有滚动元素都以相同的速度移动/不相对于彼此移动,所以您可以只为其根容器设置动画。我很确定这会给你10倍的提升。

要了解正在吃CPU周期的内容,请使用浏览器提供的javascript profiler 。 Safari也有很好的Firebug。

答案 1 :(得分:1)

例如,在你的移动功能中,可以做一些改善事情的改变。

首先,$$('.rightCont')$$('.leftCont')是每次调用函数时遍历dom的选择器。如果您不希望数组元素发生变化,为什么不将它们缓存到全局变量中,例如:

var conts = {
    left: $$("div.rightCont"),
    right: $$("div.leftCont")
};

// then just refer to them within function move like so...
conts.left.each(...); // etc.

当你在mootools中使用setStyle维度默认单位是px时,连接你的top(int)和“px”字符串是没有意义的,因为字符串是不可变的,所以IE可以放慢速度......

另外,如果您执行el.setStyle('top', n)之类的操作,那么您可以假设el.style.top将为n,而您可以if(el.getStyle('top') < h)if(parseInt(el.getStyle('top')) > 400)进行两次无意义的查找。< / p>

你可以通过为两种类型的元素做一个循环来加快速度,我估计......无论如何,gl。

使用el.getPosition().y将以int的形式到达,因此您不需要parseInt(因为框架可能会执行相同操作,因此不会节省很多cpu)。另外,当你需要parseInt时,请改用mootools'number.toInt(),它是可链接的