Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(286)

Side by Side Diff: pkg/analyzer/lib/src/generated/resolver.dart

Issue 2260313002: Extend Future.then inference to subclasses (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 4 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | pkg/analyzer/lib/src/generated/static_type_analyzer.dart » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 library analyzer.src.generated.resolver; 5 library analyzer.src.generated.resolver;
6 6
7 import 'dart:collection'; 7 import 'dart:collection';
8 8
9 import 'package:analyzer/dart/ast/ast.dart'; 9 import 'package:analyzer/dart/ast/ast.dart';
10 import 'package:analyzer/dart/ast/token.dart'; 10 import 'package:analyzer/dart/ast/token.dart';
(...skipping 5740 matching lines...) Expand 10 before | Expand all | Expand 10 after
5751 } 5751 }
5752 5752
5753 /** 5753 /**
5754 * Prepares this [ResolverVisitor] to using it for incremental resolution. 5754 * Prepares this [ResolverVisitor] to using it for incremental resolution.
5755 */ 5755 */
5756 void initForIncrementalResolution() { 5756 void initForIncrementalResolution() {
5757 _overrideManager.enterScope(); 5757 _overrideManager.enterScope();
5758 } 5758 }
5759 5759
5760 /** 5760 /**
5761 * Returns true if this method is `Future.then`. 5761 * Returns true if this method is `Future.then` or an override thereof.
5762 * 5762 *
5763 * If so we will apply special typing rules in strong mode, to handle the 5763 * If so we will apply special typing rules in strong mode, to handle the
5764 * implicit union of `S | Future<S>` 5764 * implicit union of `S | Future<S>`
5765 */ 5765 */
5766 bool isFutureThen(Element element) { 5766 bool isFutureThen(Element element) {
5767 return element is MethodElement && 5767 // If we are a method named then
5768 element.name == 'then' && 5768 if (element is MethodElement && element.name == 'then') {
5769 element.enclosingElement.type.isDartAsyncFuture; 5769 // On Future, then we're good.
5770 if (element.enclosingElement.type.isDartAsyncFuture) {
Jennifer Messerly 2016/08/19 19:36:46 could be worth a "DartType type = element.enclosin
Leaf 2016/08/19 19:47:00 Done.
5771 return true;
5772 }
5773 // On a subtype of Future we're good.
5774 if (typeSystem.isSubtypeOf(
5775 element.enclosingElement.type, typeProvider.futureDynamicType)) {
5776 return true;
5777 }
5778 }
5779 return false;
5770 } 5780 }
5771 5781
5772 /** 5782 /**
5773 * Given a downward inference type [fnType], and the declared 5783 * Given a downward inference type [fnType], and the declared
5774 * [typeParameterList] for a function expression, determines if we can enable 5784 * [typeParameterList] for a function expression, determines if we can enable
5775 * downward inference and if so, returns the function type to use for 5785 * downward inference and if so, returns the function type to use for
5776 * inference. 5786 * inference.
5777 * 5787 *
5778 * This will return null if inference is not possible. This happens when 5788 * This will return null if inference is not possible. This happens when
5779 * there is no way we can find a subtype of the function type, given the 5789 * there is no way we can find a subtype of the function type, given the
(...skipping 938 matching lines...) Expand 10 before | Expand all | Expand 10 after
6718 perBranchOverrides.add(thenOverrides); 6728 perBranchOverrides.add(thenOverrides);
6719 perBranchOverrides.add(elseOverrides); 6729 perBranchOverrides.add(elseOverrides);
6720 _overrideManager.mergeOverrides(perBranchOverrides); 6730 _overrideManager.mergeOverrides(perBranchOverrides);
6721 } 6731 }
6722 return null; 6732 return null;
6723 } 6733 }
6724 6734
6725 @override 6735 @override
6726 Object visitInstanceCreationExpression(InstanceCreationExpression node) { 6736 Object visitInstanceCreationExpression(InstanceCreationExpression node) {
6727 TypeName classTypeName = node.constructorName.type; 6737 TypeName classTypeName = node.constructorName.type;
6738 // TODO(leafp): Currently, we may re-infer types here, since we
6739 // sometimes resolve multiple times. We should really check that we
6740 // have not already inferred something. However, the obvious ways to
6741 // check this don't work, since we class may have been instantiated
6742 // to bounds in an earlier phase, and we *do* want to do inference
6743 // in that case.
6728 if (classTypeName.typeArguments == null) { 6744 if (classTypeName.typeArguments == null) {
6729 // Given a union of context types ` T0 | T1 | ... | Tn`, find the first 6745 // Given a union of context types ` T0 | T1 | ... | Tn`, find the first
6730 // valid instantiation `new C<Ti>`, if it exists. 6746 // valid instantiation `new C<Ti>`, if it exists.
6731 // TODO(jmesserly): if we support union types for real, `new C<Ti | Tj>` 6747 // TODO(jmesserly): if we support union types for real, `new C<Ti | Tj>`
6732 // will become a valid possibility. Right now the only allowed union is 6748 // will become a valid possibility. Right now the only allowed union is
6733 // `T | Future<T>` so we can take a simple approach. 6749 // `T | Future<T>` so we can take a simple approach.
6734 for (var contextType in InferenceContext.getTypes(node)) { 6750 for (var contextType in InferenceContext.getTypes(node)) {
6735 if (contextType is InterfaceType && 6751 if (contextType is InterfaceType &&
6736 contextType.typeArguments != null && 6752 contextType.typeArguments != null &&
6737 contextType.typeArguments.isNotEmpty) { 6753 contextType.typeArguments.isNotEmpty) {
(...skipping 4407 matching lines...) Expand 10 before | Expand all | Expand 10 after
11145 return null; 11161 return null;
11146 } 11162 }
11147 if (identical(node.staticElement, variable)) { 11163 if (identical(node.staticElement, variable)) {
11148 if (node.inSetterContext()) { 11164 if (node.inSetterContext()) {
11149 result = true; 11165 result = true;
11150 } 11166 }
11151 } 11167 }
11152 return null; 11168 return null;
11153 } 11169 }
11154 } 11170 }
OLDNEW
« no previous file with comments | « no previous file | pkg/analyzer/lib/src/generated/static_type_analyzer.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698