Looping through an enum, TypeScript and JQuery

2019-06-16 17:50发布

问题:

Hello im trying t develop a straight forward todo app using TypeScript and JQuery. I have an enum that lists task types:

export enum TaskType { FrontEnd, BackEnd, Designer };

However looping through the emum using jquery.each or for loop, i get the following result, (values then indexes):

        FrontEnd, BackEnd, Designer, 0, 1, 2

The following is the code i loop through the enum:

        constructor(e?: Object) {             

            var template = this.FormTemplate;

            $(e).append(template);

            var sel = template.find('select');

            /*$.each(TaskType, function (index, el) {
                sel.append("<option value='" + index + "'>" + el + "</option>");
            });*/

            for(var i=0; i < (typeof TaskType).length; i++){
                sel.append("<option value='" + TaskType[i] + "'>" + TaskType[i] + "</option>");
            }

        }

Can someone tell me why this is?

回答1:

TypeScript enums when compiled into plain JS contain both the symbolic name AND the numeric values as properties and that explains why you get FrontEnd, BackEnd, Designer, 0, 1, 2 when you try to enumerate the properties of the object. As best I know, there is no post-compile way to enumerate only the symbolic names. You could enumerate all of them and skip anything that is a number.

From this article, you can see exactly how a TypeScript enum compiles into JS.

If you have this TypeScript:

//TypeScript declaration:
enum StandardEnum {FirstItem, SecondItem, ThirdItem};

It compiles to this Javscript:

//Compiled javascript:
var StandardEnum;
(function (StandardEnum) {
    StandardEnum[StandardEnum["FirstItem"] = 0] = "FirstItem";
    StandardEnum[StandardEnum["SecondItem"] = 1] = "SecondItem";
    StandardEnum[StandardEnum["ThirdItem"] = 2] = "ThirdItem";
})(StandardEnum || (StandardEnum = {}));
;

Which is essentially this result:

var StandardEnum = {
    "FirstItem": 0,
    "SecondItem": 1,
    "ThirdItem": 2,
    "0": "FirstItem",
    "1": "SecondItem",
    "2": "ThirdItem"
};

So, unless you specifically ignore the numeric properties, there is no way to enumerate just the enum names.

You could do that like this:

 for (var item in StandardEnum) {
     if (StandardEnum.hasOwnProperty(item) && !/^\d+$/.test(item)) {
         console.log(item);
     }
 }

Working demo: http://jsfiddle.net/jfriend00/65cfg88u/


FYI, if what you really want is:

var StandardEnum = {
    "FirstItem": 0,
    "SecondItem": 1,
    "ThirdItem": 2
};

Then, maybe you should not use the enum and just use this standard JS declaration. Then, you could get the properties with Object.keys(StandardEnum).