Javascript Orderby未在ng repeat上使用dict语法

Javascript Orderby未在ng repeat上使用dict语法,javascript,angularjs,angularjs-orderby,Javascript,Angularjs,Angularjs Orderby,我试图使用字典式语法的ng repeat,并对键值应用一个顺序 某物中的(键、值)| orderBy:'key' OrderBy似乎没有按预期工作 这里的例子 这是没有实现的。请看这里: 编辑(2013年8月27日):这个问题现在似乎已得到解决。orderBy的参数必须与对象数组中的属性名称匹配 您的数据需要如下所示: $scope.list2 = [ { id:"2013-01-08T00:00:00", name:'Joe'}, { id:"2013-01

我试图使用字典式语法的ng repeat,并对键值应用一个顺序

某物中的
(键、值)| orderBy:'key'

OrderBy似乎没有按预期工作

这里的例子

这是没有实现的。请看这里:


编辑(2013年8月27日):这个问题现在似乎已得到解决。

orderBy的参数必须与对象数组中的属性名称匹配

您的数据需要如下所示:

$scope.list2 = [ { id:"2013-01-08T00:00:00", name:'Joe'},
                 { id:"2013-01-09T00:00:00", name:'Sue'}];
这样的过滤器就可以工作了:

<div ng-repeat="item in list2 | orderBy:'id':true">


请注意,orderBy对整个数组(上面示例代码中的
something
)起作用,并返回一个排序数组。orderBy对

一无所知。我创建了一个自定义筛选器,使选择列表可以执行此操作:

.filter('toDictionaryArray', function () {
    return function (obj) {
        if (!(obj instanceof Object)) return obj;

        var arr = [];
        for (var key in obj) {
            arr.push({ key: key, value: obj[key] });
        }
        return arr;
    }
})
然后,选择列表ng选项的内容如下:

<select ng-options="kv.key as kv.value for kv in p.options | toDictionaryArray | orderBy:'value'"></select>

正如akonsu所说,该功能已被请求。然而,我仍然无法让它与最新的(1.3.0)测试版配合使用

注释中隐藏了一个注释(注意这需要,在上面的示例中,您必须将对“key”的引用替换为“value.$key”):

[添加筛选器]:

app.filter('toArray', function() { return function(obj) {
    if (!(obj instanceof Object)) return obj;
    return _.map(obj, function(val, key) {
        return Object.defineProperty(val, '$key', {__proto__: null, value: key});
    });
}});
标记示例:

<div ng-repeat="val in object | toArray | orderBy:'priority' | filter:fieldSearch">
  {{val.$key}} : {{val}} 
</div>

{{val.$key}}:{{val}
潜在的不利因素:

  • Object.defineProperty在IE8中不会像这样工作(如果您不这样做的话) 请注意使$key可枚举,然后这是一个简单的更改)
  • 如果属性值不是对象,则无法设置$key属性 这是失败的
  • 它没有直接集成到orderBy或ngRepeat中 所以语法是不同的
这里有一个很好的解决方法():


而不是使用仅支持数组而不支持对象的orderby筛选器。您可以像这样编写自己的过滤器。我从Justin Klemm那里获取了代码,并添加了对指定多个排序字段的支持。下面的过滤器示例是基于值中的属性进行过滤,但您也可以轻松地将其更改为基于键进行过滤

app.filter('orderObjectBy', function()
{
    return function(items, fields, reverse)
    {
        var filtered = [];
        angular.forEach(items, function(item)
        {
            filtered.push(item);
        });

        filtered.sort(function (a, b)
        {
            var result = 0;

            for (var i = 0; i < fields.length; ++i)
            {
                if (a[fields[i]] > b[fields[i]])
                {
                    result = 1;
                    break;
                }
                else if (a[fields[i]] < b[fields[i]])
                {
                    result = -1;
                    break;
                }
            }

            return result;
        });

        if (reverse)
        {
            filtered.reverse();
        }

        return filtered;
    };
});
app.filter('orderObjectBy',function()
{
返回函数(项目、字段、反向)
{
var筛选=[];
角度。forEach(项目、功能(项目)
{
过滤、推送(项目);
});
筛选.排序(函数(a,b)
{
var结果=0;
对于(变量i=0;ib[fields[i]])
{
结果=1;
打破
}
else if(a[fields[i]]
然后在你的html5网页中,像这样使用它,统计是一个带有键值对的地图/字典

<div class="row" ng-repeat="stat in statistics | orderObjectBy: 'NumTimesPartnered', 'NumTimesOpponent']:true">
    <div class="col col-33">{{stat.Name}}</div>
    <div class="col"><center>{{stat.NumTimesPartnered}}</center></div>
    <div class="col"><center>{{stat.NumTimesOpponent}}</center></div>
</div>

{{stat.Name}}
{{stat.numtimespartned}}
{{stat.numtimesoponent}}

@akonsu,说得好。我认为它不能与字典语法一起工作。我对我的答案进行了一些编辑。谢谢大家,我使用了下划线,所以我用map函数修复了它-最后一点对我来说是重要的一点。我希望angular发送一个新数组,该数组的结构匹配(键、值)。相反,它是基于最初的列表,我的问题是我没有使用引号。您好,您能告诉我下面的提琴有什么问题吗?虽然我不反对链接到解决问题的图书馆,但我反对使用提供的解决方案且未经认证的建议。链接库比我建议的解决方案做的更多。为什么要使用
defineProperty
而不是
val.$key=key
?好问题-根据代码作者的说法(请参见链接),“一个简单的更改是替换return对象。defineProperty(val,$key',{proto:null,value:key});使用val.$key=key;return val;”。看起来您可以使用赋值,但需要添加一个return语句。
<div class="row" ng-repeat="stat in statistics | orderObjectBy: 'NumTimesPartnered', 'NumTimesOpponent']:true">
    <div class="col col-33">{{stat.Name}}</div>
    <div class="col"><center>{{stat.NumTimesPartnered}}</center></div>
    <div class="col"><center>{{stat.NumTimesOpponent}}</center></div>
</div>