{"action":"created","issue":{"url":"https://api.github.com/repos/Microsoft/TypeScript/issues/6223","labels_url":"https://api.github.com/repos/Microsoft/TypeScript/issues/6223/labels{/name}","comments_url":"https://api.github.com/repos/Microsoft/TypeScript/issues/6223/comments","events_url":"https://api.github.com/repos/Microsoft/TypeScript/issues/6223/events","html_url":"https://github.com/Microsoft/TypeScript/issues/6223","id":123644145,"number":6223,"title":"Polymorphic `this` and Generics","user":{"login":"kitsonk","id":1282577,"avatar_url":"https://avatars.githubusercontent.com/u/1282577?v=3","gravatar_id":"","url":"https://api.github.com/users/kitsonk","html_url":"https://github.com/kitsonk","followers_url":"https://api.github.com/users/kitsonk/followers","following_url":"https://api.github.com/users/kitsonk/following{/other_user}","gists_url":"https://api.github.com/users/kitsonk/gists{/gist_id}","starred_url":"https://api.github.com/users/kitsonk/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/kitsonk/subscriptions","organizations_url":"https://api.github.com/users/kitsonk/orgs","repos_url":"https://api.github.com/users/kitsonk/repos","events_url":"https://api.github.com/users/kitsonk/events{/privacy}","received_events_url":"https://api.github.com/users/kitsonk/received_events","type":"User","site_admin":false},"labels":[],"state":"open","locked":false,"assignee":null,"milestone":null,"comments":3,"created_at":"2015-12-23T11:35:23Z","updated_at":"2015-12-23T13:01:26Z","closed_at":null,"body":"First, thank you team for polymorphic `this`.  It is really handy!\r\n\r\nI think I ran into a case though that I am finding challenging, when I need to return a `this`, but the generics might have changed.  For example:\r\n\r\n```typescript\r\nclass A<T> {\r\n    private items: T[] = [];\r\n    map<U>(callback: (item: T, idx: number, a: this) => U): this {\r\n        // boring implementation details\r\n    });\r\n}\r\n```\r\n\r\nWhere I want to be able to change the generic type for the class with a function, but I will be contracting to return the \"current\" class, but I want to guard different generics.  The following seems logical to me, but doesn't appear to be currently supported:\r\n\r\n```typescript\r\nclass A<T> {\r\n    private items: T[] = [];\r\n    map<U>(callback: (item: T, idx: number, a: this) => U): this<U> {\r\n        // boring implementation details\r\n    });\r\n}\r\n```\r\n\r\nWhere if no generics arguments are supplied, it is inferred to be the current ones, where as if they are supplied they are substituted."},"comment":{"url":"https://api.github.com/repos/Microsoft/TypeScript/issues/comments/166889899","html_url":"https://github.com/Microsoft/TypeScript/issues/6223#issuecomment-166889899","issue_url":"https://api.github.com/repos/Microsoft/TypeScript/issues/6223","id":166889899,"user":{"login":"kitsonk","id":1282577,"avatar_url":"https://avatars.githubusercontent.com/u/1282577?v=3","gravatar_id":"","url":"https://api.github.com/users/kitsonk","html_url":"https://github.com/kitsonk","followers_url":"https://api.github.com/users/kitsonk/followers","following_url":"https://api.github.com/users/kitsonk/following{/other_user}","gists_url":"https://api.github.com/users/kitsonk/gists{/gist_id}","starred_url":"https://api.github.com/users/kitsonk/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/kitsonk/subscriptions","organizations_url":"https://api.github.com/users/kitsonk/orgs","repos_url":"https://api.github.com/users/kitsonk/repos","events_url":"https://api.github.com/users/kitsonk/events{/privacy}","received_events_url":"https://api.github.com/users/kitsonk/received_events","type":"User","site_admin":false},"created_at":"2015-12-23T13:01:26Z","updated_at":"2015-12-23T13:01:26Z","body":"@myitcv thanks, but I don't think it does.  I am not talking about inferring higher-order types as seems to be discussed there.  I am actually talking about replacing generic type slots with other values in a polymorphic `this` so that the resulting types can accurately reflect the runtime behaviour of some code.\r\n\r\nTo express where this becomes a problem, I will extend the class:\r\n\r\n```typescript\r\nclass A<T> {\r\n    private items: T[] = [];\r\n    map<U>(callback: (item: T, idx: number, a: this) => U): A<U> {\r\n        // boring implementation details\r\n    });\r\n}\r\n\r\nclass B<T> extends A<T> {\r\n    foo(): void {};\r\n}\r\n\r\nconst b = new B<string>().map((item) => Number(item));\r\n// b will be typed as A<number> not B<number>\r\n```\r\n\r\n**or**\r\n\r\n```typescript\r\nclass A<T> {\r\n    private items: T[] = [];\r\n    map<U>(callback: (item: T, idx: number, a: this) => U): this {\r\n        // boring implementation details\r\n    });\r\n}\r\n\r\nclass B<T> extends A<T> {\r\n    foo(): void {};\r\n}\r\n\r\nconst b = new B<string>().map((item) => Number(item));\r\n// b will be typed as B<string> not B<number>\r\n```\r\n"}}