Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
lwm1986
roslyn
提交
bc9be6c0
R
roslyn
项目概览
lwm1986
/
roslyn
与 Fork 源项目一致
从无法访问的项目Fork
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
R
roslyn
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
bc9be6c0
编写于
5月 09, 2017
作者:
S
Sam Harwell
提交者:
GitHub
5月 09, 2017
浏览文件
操作
浏览文件
下载
差异文件
Merge pull request #19258 from sharwell/candidate-test
Verify member is in scope before trying to replace it
上级
3986cdb6
c6f25f62
变更
3
隐藏空白更改
内联
并排
Showing
3 changed file
with
118 addition
and
1 deletion
+118
-1
src/EditorFeatures/Test2/Simplification/TypeNameSimplifierTest.vb
...orFeatures/Test2/Simplification/TypeNameSimplifierTest.vb
+2
-1
src/Workspaces/CSharp/Portable/Extensions/ExpressionSyntaxExtensions.cs
.../CSharp/Portable/Extensions/ExpressionSyntaxExtensions.cs
+113
-0
src/Workspaces/Core/Portable/Utilities/ImmutableArrayExtensions.cs
...paces/Core/Portable/Utilities/ImmutableArrayExtensions.cs
+3
-0
未找到文件。
src/EditorFeatures/Test2/Simplification/TypeNameSimplifierTest.vb
浏览文件 @
bc9be6c0
...
...
@@ -764,7 +764,8 @@ namespace N1
Await
TestAsync
(
input
,
expected
)
End
Function
<
Fact
,
Trait
(
Traits
.
Feature
,
Traits
.
Features
.
Simplification
)
>
<
Fact
(
Skip
:
=
"https://github.com/dotnet/roslyn/issues/19368"
)
>
<
Trait
(
Traits
.
Feature
,
Traits
.
Features
.
Simplification
)
>
Public
Async
Function
TestSimplifyNot_Delegate1
()
As
Task
Dim
input
=
<
Workspace
>
...
...
src/Workspaces/CSharp/Portable/Extensions/ExpressionSyntaxExtensions.cs
浏览文件 @
bc9be6c0
...
...
@@ -2,6 +2,7 @@
using
System
;
using
System.Collections.Generic
;
using
System.Collections.Immutable
;
using
System.Linq
;
using
System.Threading
;
using
Microsoft.CodeAnalysis.CodeStyle
;
...
...
@@ -799,6 +800,27 @@ private static bool CanReplace(ISymbol symbol)
}
}
// Try to eliminate cases without actually calling CanReplaceWithReducedName. For expressions of the form
// 'this.Name' or 'base.Name', no additional check here is required.
if
(!
memberAccess
.
Expression
.
IsKind
(
SyntaxKind
.
ThisExpression
,
SyntaxKind
.
BaseExpression
))
{
var
actualSymbol
=
semanticModel
.
GetSymbolInfo
(
memberAccess
.
Name
,
cancellationToken
);
if
(!
TryGetReplacementCandidates
(
semanticModel
,
memberAccess
,
actualSymbol
,
out
var
speculativeSymbols
,
out
var
speculativeNamespacesAndTypes
))
{
return
false
;
}
if
(!
IsReplacementCandidate
(
actualSymbol
,
speculativeSymbols
,
speculativeNamespacesAndTypes
))
{
return
false
;
}
}
replacementNode
=
memberAccess
.
Name
.
WithLeadingTrivia
(
memberAccess
.
GetLeadingTriviaForSimplifiedMemberAccess
())
.
WithTrailingTrivia
(
memberAccess
.
GetTrailingTrivia
());
...
...
@@ -812,6 +834,97 @@ private static bool CanReplace(ISymbol symbol)
return
memberAccess
.
CanReplaceWithReducedName
(
replacementNode
,
semanticModel
,
cancellationToken
);
}
private
static
bool
TryGetReplacementCandidates
(
SemanticModel
semanticModel
,
MemberAccessExpressionSyntax
memberAccess
,
SymbolInfo
actualSymbol
,
out
ImmutableArray
<
ISymbol
>
speculativeSymbols
,
out
ImmutableArray
<
ISymbol
>
speculativeNamespacesAndTypes
)
{
bool
containsNamespaceOrTypeSymbol
;
bool
containsOtherSymbol
;
if
(!(
actualSymbol
.
Symbol
is
null
))
{
containsNamespaceOrTypeSymbol
=
actualSymbol
.
Symbol
is
INamespaceOrTypeSymbol
;
containsOtherSymbol
=
!
containsNamespaceOrTypeSymbol
;
}
else
if
(!
actualSymbol
.
CandidateSymbols
.
IsDefaultOrEmpty
)
{
containsNamespaceOrTypeSymbol
=
actualSymbol
.
CandidateSymbols
.
Any
(
symbol
=>
symbol
is
INamespaceOrTypeSymbol
);
containsOtherSymbol
=
actualSymbol
.
CandidateSymbols
.
Any
(
symbol
=>
!(
symbol
is
INamespaceOrTypeSymbol
));
}
else
{
speculativeSymbols
=
ImmutableArray
<
ISymbol
>.
Empty
;
speculativeNamespacesAndTypes
=
ImmutableArray
<
ISymbol
>.
Empty
;
return
false
;
}
speculativeSymbols
=
containsOtherSymbol
?
semanticModel
.
LookupSymbols
(
memberAccess
.
SpanStart
,
name
:
memberAccess
.
Name
.
Identifier
.
ValueText
)
:
ImmutableArray
<
ISymbol
>.
Empty
;
speculativeNamespacesAndTypes
=
containsNamespaceOrTypeSymbol
?
semanticModel
.
LookupNamespacesAndTypes
(
memberAccess
.
SpanStart
,
name
:
memberAccess
.
Name
.
Identifier
.
ValueText
)
:
ImmutableArray
<
ISymbol
>.
Empty
;
return
true
;
}
/// <summary>
/// Determines if <paramref name="speculativeSymbols"/> and <paramref name="speculativeNamespacesAndTypes"/>
/// together contain a superset of the symbols in <paramref name="actualSymbol"/>.
/// </summary>
private
static
bool
IsReplacementCandidate
(
SymbolInfo
actualSymbol
,
ImmutableArray
<
ISymbol
>
speculativeSymbols
,
ImmutableArray
<
ISymbol
>
speculativeNamespacesAndTypes
)
{
if
(
speculativeSymbols
.
IsEmpty
&&
speculativeNamespacesAndTypes
.
IsEmpty
)
{
return
false
;
}
if
(!(
actualSymbol
.
Symbol
is
null
))
{
return
speculativeSymbols
.
Contains
(
actualSymbol
.
Symbol
,
CandidateSymbolEqualityComparer
.
Instance
)
||
speculativeNamespacesAndTypes
.
Contains
(
actualSymbol
.
Symbol
,
CandidateSymbolEqualityComparer
.
Instance
);
}
foreach
(
var
symbol
in
actualSymbol
.
CandidateSymbols
)
{
if
(!
speculativeSymbols
.
Contains
(
symbol
,
CandidateSymbolEqualityComparer
.
Instance
)
&&
!
speculativeNamespacesAndTypes
.
Contains
(
symbol
,
CandidateSymbolEqualityComparer
.
Instance
))
{
return
false
;
}
}
return
true
;
}
/// <summary>
/// Compares symbols by their original definition.
/// </summary>
private
sealed
class
CandidateSymbolEqualityComparer
:
IEqualityComparer
<
ISymbol
>
{
public
static
CandidateSymbolEqualityComparer
Instance
{
get
;
}
=
new
CandidateSymbolEqualityComparer
();
private
CandidateSymbolEqualityComparer
()
{
}
public
bool
Equals
(
ISymbol
x
,
ISymbol
y
)
{
if
(
x
is
null
||
y
is
null
)
{
return
x
==
y
;
}
return
x
.
OriginalDefinition
.
Equals
(
y
.
OriginalDefinition
);
}
public
int
GetHashCode
(
ISymbol
obj
)
{
return
obj
?.
OriginalDefinition
.
GetHashCode
()
??
0
;
}
}
private
static
SyntaxTriviaList
GetLeadingTriviaForSimplifiedMemberAccess
(
this
MemberAccessExpressionSyntax
memberAccess
)
{
// We want to include any user-typed trivia that may be present between the 'Expression', 'OperatorToken' and 'Identifier' of the MemberAccessExpression.
...
...
src/Workspaces/Core/Portable/Utilities/ImmutableArrayExtensions.cs
浏览文件 @
bc9be6c0
...
...
@@ -8,6 +8,9 @@ namespace Roslyn.Utilities
{
internal
static
class
ImmutableArrayExtensions
{
internal
static
bool
Contains
<
T
>(
this
ImmutableArray
<
T
>
items
,
T
item
,
IEqualityComparer
<
T
>
equalityComparer
)
=>
items
.
IndexOf
(
item
,
0
,
equalityComparer
)
>=
0
;
internal
static
ImmutableArray
<
T
>
ToImmutableArrayOrEmpty
<
T
>(
this
T
[]
items
)
{
if
(
items
==
null
)
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录