0

typescript中的Array类没有像AS3那样的sortOn方法,在github上找了一个库,
https://github.com/gonchuki/m...

就一个文件,但这个文件中sortOn方法是动态生成的。代码如下

/*
---
script: Array.sortOn.js
description: Adds Array.sortOn function and related constants that works like in ActionScript for sorting arrays of objects (applying all same strict rules)
license: MIT-style license.
authors:
- gonchuki
docs: http://www.adobe.com/livedocs/flash/9.0/ActionScriptLangRefV3/Array.html#sortOn()
requires:
- core/1.2.4: [Array]
provides: 
- [Array.sortOn, Array.CASEINSENSITIVE, Array.DESCENDING, Array.UNIQUESORT, Array.RETURNINDEXEDARRAY, Array.NUMERIC]
...
*/

Array.CASEINSENSITIVE = 1;
Array.DESCENDING = 2;
Array.UNIQUESORT = 4;
Array.RETURNINDEXEDARRAY = 8;
Array.NUMERIC = 16;

(function() {
  var dup_fn = function(field, field_options) {
    var filtered = (field_options & Array.NUMERIC) 
                   ? this.map(function(item) {return item[field].toFloat(); })
                   : (field_options & Array.CASEINSENSITIVE)
                   ? this.map(function(item) {return item[field].toLowerCase(); })
                   : this.map(function(item) {return item[field]; });
    return filtered.length !== [].combine(filtered).length;
  };
  
  var sort_fn = function(item_a, item_b, fields, options) {
    return (function sort_by(fields, options) {
      var ret, a, b, 
          opts = options[0],
          sub_fields = fields[0].match(/[^.]+/g);
      
      (function get_values(s_fields, s_a, s_b) {
        var field = s_fields[0];
        if (s_fields.length > 1) {
          get_values(s_fields.slice(1), s_a[field], s_b[field]);
        } else {
          a = s_a[field].toString();
          b = s_b[field].toString();
        }
      })(sub_fields, item_a, item_b);
      
      if (opts & Array.NUMERIC) {
        ret = (a.toFloat() - b.toFloat());
      } else {
        if (opts & Array.CASEINSENSITIVE) { a = a.toLowerCase(); b = b.toLowerCase(); }
        
        ret = (a > b) ? 1 : (a < b) ? -1 : 0;
      }
      
      if ((ret === 0) && (fields.length > 1)) {
        ret = sort_by(fields.slice(1), options.slice(1));
      } else if (opts & Array.DESCENDING) {
        ret *= -1;
      }
      
      return ret;
    })(fields, options);
  };
  
  Array.implement({
    sortOn: function(fields, options) {
      fields = $splat(fields);
      options = $splat(options);
      
      if (options.length !== fields.length) options = [];
      
      if ((options[0] & Array.UNIQUESORT) && (fields.some(function(field, i){return dup_fn(field, options[i]);}))) return 0;
      
      var curry_sort = function(item_a, item_b) {
        return sort_fn(item_a, item_b, fields, options);
      };
      
      if (options[0] & Array.RETURNINDEXEDARRAY)
        return this.slice().sort(curry_sort);
      else
        this.sort(curry_sort);
    }
  });
  
})();

我在TS项目里增加了这个类的引用,并尝试写了.d.ts文件

interface Array<T> {
    CASEINSENSITIVE;
    DESCENDING;
    UNIQUESORT;
    RETURNINDEXEDARRAY;
    NUMERIC;
    
    sortOn(fields, options):any;
}

代码里可以调用到sortOn方法,编译不报错。但运行时sortOn方法是undefined的。
谁试过这种情况?该如何设置js文件,以及如何写这个.d.ts文件
或者我怎么才能给Array加上sortOn方法?

5 天前提问
2 个回答
0

已采纳

用了这个库sort-on-as3
他自己提供了一个.d.ts的文件。
TS代码中,使用sortOn之前,在全局加上以下代码:

const sortOn = require('sort-on-as3');
sortOn.extend(Array);

亲测可用。
但本问题仍然没有解决:动态生成的js方法,.d.ts文件里要怎么写?

1
  1. Array不是定义在globals.d.ts吗。
  2. 不要改原生的定义,否则你一错影响的范围不知道有多广。
  3. 继承一个Array,通过(arr as MyArray).sortOn访问。

撰写答案

推广链接