Skip to content

Commit de88556

Browse files
committed
Reduced inspection complexity from O(you've got to be shitting me) to O(k).
1 parent d654372 commit de88556

File tree

1 file changed

+25
-45
lines changed

1 file changed

+25
-45
lines changed

RetailCoder.VBE/Inspections/ProcedureCanBeWrittenAsFunctionInspection.cs

Lines changed: 25 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
11
using System.Collections.Generic;
22
using System.Linq;
3+
using System.Security.Policy;
34
using Rubberduck.Common;
45
using Rubberduck.Parsing;
56
using Rubberduck.Parsing.Grammar;
7+
using Rubberduck.Parsing.Symbols;
68
using Rubberduck.Parsing.VBA;
79
using NLog;
810
using Rubberduck.Inspections.Abstract;
@@ -39,52 +41,30 @@ public override IEnumerable<InspectionResultBase> GetInspectionResults()
3941
Logger.Debug("Aborting GetInspectionResults because ParseTree results were not passed");
4042
return new InspectionResultBase[] { };
4143
}
42-
var subStmts = ParseTreeResults.OfType<QualifiedContext<VBAParser.ArgListContext>>()
43-
.Where(context => context.Context.Parent is VBAParser.SubStmtContext)
44-
.Select(context => (VBAParser.SubStmtContext)context.Context.Parent)
45-
.ToList();
4644

47-
var subStmtsNotImplementingInterfaces = subStmts
48-
.Where(c =>
49-
{
50-
var declaration =
51-
UserDeclarations.SingleOrDefault(d => d.Context == c);
52-
53-
if (UserDeclarations.FindInterfaceMembers().Contains(declaration))
54-
{
55-
return false;
56-
}
57-
58-
var interfaceImplementation = UserDeclarations.FindInterfaceImplementationMembers().SingleOrDefault(m => m.Equals(declaration));
59-
if (interfaceImplementation == null)
60-
{
61-
return true;
62-
}
63-
64-
var interfaceMember = UserDeclarations.FindInterfaceMember(interfaceImplementation);
65-
66-
return interfaceMember == null;
67-
});
68-
69-
var subStmtsNotImplementingEvents = subStmts
70-
.Where(c =>
71-
{
72-
var declaration = UserDeclarations.SingleOrDefault(d => d.Context == c);
73-
74-
if (declaration == null) { return false; } // rather be safe than sorry
75-
76-
return UserDeclarations.Where(item => item.IsWithEvents)
77-
.All(withEvents => UserDeclarations.FindEventProcedures(withEvents) == null) &&
78-
!State.AllDeclarations.FindBuiltInEventHandlers().Contains(declaration);
79-
});
80-
81-
return ParseTreeResults
82-
.Where(result => result.Context.Parent is VBAParser.SubStmtContext &&
83-
subStmtsNotImplementingInterfaces.Contains(result.Context.Parent) &&
84-
subStmtsNotImplementingEvents.Contains(result.Context.Parent)
85-
&& !IsIgnoringInspectionResultFor(result.ModuleName.Component, result.Context.Start.Line))
86-
.Select(result => new ProcedureCanBeWrittenAsFunctionInspectionResult(this, State, result,
87-
new QualifiedContext<VBAParser.SubStmtContext>(result.ModuleName, result.Context.Parent as VBAParser.SubStmtContext)));
45+
var userDeclarations = UserDeclarations.ToList();
46+
var allDeclarations = State.AllDeclarations.ToList();
47+
48+
var contextLookup = userDeclarations.Where(decl => decl.Context != null).ToDictionary(decl => decl.Context);
49+
50+
var ignored = new HashSet<Declaration>( State.DeclarationFinder.FindAllInterfaceMembers()
51+
.Concat(State.DeclarationFinder.FindAllInterfaceImplementingMembers())
52+
.Concat(allDeclarations.FindBuiltInEventHandlers())
53+
.Concat(userDeclarations.Where(item => item.IsWithEvents)));
54+
55+
return ParseTreeResults.Where(context => context.Context.Parent is VBAParser.SubStmtContext)
56+
.Select(context => contextLookup[(VBAParser.SubStmtContext)context.Context.Parent])
57+
.Where(decl => !IsIgnoringInspectionResultFor(decl, AnnotationName) &&
58+
!ignored.Contains(decl) &&
59+
userDeclarations.Where(item => item.IsWithEvents)
60+
.All(withEvents => userDeclarations.FindEventProcedures(withEvents) == null) &&
61+
!allDeclarations.FindBuiltInEventHandlers().Contains(decl))
62+
.Select(result => new ProcedureCanBeWrittenAsFunctionInspectionResult(
63+
this,
64+
State,
65+
new QualifiedContext<VBAParser.ArgListContext>(result.QualifiedName,result.Context.GetChild<VBAParser.ArgListContext>(0)),
66+
new QualifiedContext<VBAParser.SubStmtContext>(result.QualifiedName, (VBAParser.SubStmtContext)result.Context))
67+
);
8868
}
8969

9070
public class SingleByRefParamArgListListener : VBAParserBaseListener

0 commit comments

Comments
 (0)