it-swarm.dev

TypeScript وظيفة الحمولة الزائدة

يتحدث القسم 6.3 من مواصفات لغة TypeScript عن التحميل الزائد للوظائف ويعطي أمثلة ملموسة على كيفية تنفيذ ذلك. لكن إذا جربت شيئًا كهذا:

export class LayerFactory { 

    constructor (public styleFactory: Symbology.StyleFactory) { }

    createFeatureLayer (userContext : Model.UserContext, mapWrapperObj : MapWrapperBase) : any {           
         throw "not implemented";
    }                 

    createFeatureLayer(layerName : string, style : any) : any {
        throw "not implemented";
     }        

}

أحصل على خطأ مترجم يشير إلى معرف مكرر على الرغم من أن المعلمات الدالة من أنواع مختلفة. حتى لو قمت بإضافة معلمة إضافية إلى الدالة createFeatureLayer الثانية ، ما زلت أحصل على خطأ في برنامج التحويل البرمجي. الأفكار ، من فضلك.

193
Klaus Nji

قد يكون هذا لأنه عندما يتم تجميع كلتا الوظيفتين إلى JavaScript ، يكون توقيعهما متطابقًا تمامًا. نظرًا لأن JavaScript لا يحتوي على أنواع ، فقد انتهى بنا الأمر إلى إنشاء وظيفتين تأخذان نفس عدد الوسائط. لذلك ، يقيدنا TypeScript من إنشاء مثل هذه الوظائف.

يدعم TypeScript التحميل الزائد استنادًا إلى عدد المعلمات ، لكن الخطوات التي يجب اتباعها تختلف قليلاً إذا ما قورننا بـ OO اللغات. رداً على سؤال SO آخر ، شرحه أحدهم بمثال لطيف: طريقة التحميل الزائد؟ .

في الأساس ، ما نقوم به هو أننا نقوم بإنشاء وظيفة واحدة فقط وعدد من الإعلانات حتى لا يعطي TypeScript أخطاء في الترجمة. عند ترجمة هذا الرمز إلى JavaScript ، ستكون الوظيفة الملموسة وحدها مرئية. نظرًا لأنه يمكن استدعاء وظيفة JavaScript عن طريق تمرير وسيطات متعددة ، فإنها تعمل فقط.

160
S. Ravi Kiran

عند التحميل الزائد في TypeScript ، يكون لديك تطبيق واحد فقط بتوقيعات متعددة.

class Foo {
    myMethod(a: string);
    myMethod(a: number);
    myMethod(a: number, b: string);
    myMethod(a: any, b?: string) {
        alert(a.toString());
    }
}

يتم التعرف على الأحمال الزائدة الثلاثة فقط بواسطة TypeScript كتوقيعات ممكنة لاستدعاء الطريقة ، وليس التنفيذ الفعلي.

في حالتك ، سأستخدم شخصيا طريقتين بأسماء مختلفة ، حيث لا يوجد ما يكفي من القواسم المشتركة في المعلمات ، مما يجعل من المحتمل أن يحتاج الجسم إلى الكثير من "ifs" لتقرير ما يجب القيام به.

TypeScript 1.4

اعتبارا من TypeScript 1.4 ، يمكنك عادة إزالة الحاجة إلى التحميل الزائد باستخدام نوع الاتحاد. يمكن التعبير عن المثال أعلاه بشكل أفضل باستخدام:

myMethod(a: string | number, b?: string) {
    alert(a.toString());
}

نوع a هو "إما string أو number".

174
Fenton

يمكنك التصريح/ وظيفة overloaded بالإعلان عن الوظيفة على أنها نوع يحتوي على توقيعات استدعاء متعددة:

interface IFoo
{
    bar: {
        (s: string): number;
        (n: number): string;
    }
}

ثم ما يلي:

var foo1: IFoo = ...;

var n: number = foo1.bar('baz');     // OK
var s: string = foo1.bar(123);       // OK
var a: number[] = foo1.bar([1,2,3]); // ERROR

يجب أن يكون الفعل التعريف للدالة مفردًا وأن يؤدي الإرسال المناسب داخليًا على وسيطاته.

على سبيل المثال ، باستخدام فئة (يمكن أن تطبق IFoo ، لكن ليس من الضروري أن):

class Foo
{
    public bar(s: string): number;
    public bar(n: number): string;
    public bar(arg: any): any 
    {
        if (typeof(arg) === 'number')
            return arg.toString();
        if (typeof(arg) === 'string')
            return arg.length;
    }
}

ما يثير الاهتمام هنا هو أن النموذج any مخفي بواسطة التخطيات المكتوبة بشكل أكثر تحديدًا.

var foo2: new Foo();

var n: number = foo2.bar('baz');     // OK
var s: string = foo2.bar(123);       // OK
var a: number[] = foo2.bar([1,2,3]); // ERROR
38
Drew Noakes

كرؤوس للآخرين ، لقد اكتشفت أنه على الأقل كما يتضح من TypeScript المترجمة بواسطة WebPack لـ Angular 2 ، فإنك تحصل على الكتابة بهدوء بدلاً من أساليب overLOADED.

myComponent {
  method(): { console.info("no args"); },
  method(arg): { console.info("with arg"); }
}

الدعوة:

myComponent.method()

يبدو أنه ينفذ الأسلوب باستخدام الوسائط ، متجاهلاً بصمت إصدار no-arg ، مع الإخراج:

with arg
1
mtyson