Advertisement
Guest User

ReSharper Math.Pow Inlining Plugin

a guest
May 4th, 2012
192
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 3.80 KB | None | 0 0
  1. using System;
  2. using System.Linq;
  3. using JetBrains.Application;
  4. using JetBrains.Application.Progress;
  5. using JetBrains.ProjectModel;
  6. using JetBrains.ReSharper.Daemon;
  7. using JetBrains.ReSharper.Daemon.Stages;
  8. using JetBrains.ReSharper.Daemon.Stages.Dispatcher;
  9. using JetBrains.ReSharper.Feature.Services.Bulbs;
  10. using JetBrains.ReSharper.Psi.CSharp;
  11. using JetBrains.ReSharper.Psi.CSharp.Tree;
  12. using JetBrains.ReSharper.Psi.ExtensionsAPI.Tree;
  13. using JetBrains.ReSharper.Psi.Tree;
  14. using JetBrains.TextControl;
  15. using JetBrains.Util;
  16.  
  17. namespace Stuff
  18. {
  19.   [ElementProblemAnalyzer(new[] { typeof(IInvocationExpression) },
  20.     HighlightingTypes = new[] { typeof(IntPowerHighlighting) })]
  21.   public class IntPowerProblemAnalyzer : ElementProblemAnalyzer<IInvocationExpression>
  22.   {
  23.     protected override void Run(IInvocationExpression element,
  24.       ElementProblemAnalyzerData data, IHighlightingConsumer consumer)
  25.     {
  26.       bool functionIsCalledPow = false;
  27.       var e = element.InvokedExpression as IReferenceExpression;
  28.       if (e != null)
  29.       {
  30.         if (e.Reference.GetName().Equals("Pow"))
  31.           functionIsCalledPow = true;
  32.       }
  33.  
  34.       bool firstArgIsIdentifier = false;
  35.       bool secondArgIsInteger = false;
  36.       int power = -1;
  37.       if (element.Arguments.Count == 2)
  38.       {
  39.         firstArgIsIdentifier = element.Arguments[0].Value is IReferenceExpression;
  40.         var secondArg = element.Arguments[1].Value as ICSharpLiteralExpression;
  41.         if (secondArg != null && (secondArg.IsConstantValue()))
  42.         {
  43.           double value = -1.0;
  44.           var cv = secondArg.ConstantValue;
  45.           if (cv.IsDouble())
  46.             value = (double)cv.Value;
  47.           else if (cv.IsInteger())
  48.             value = (int)cv.Value;
  49.           power = (int)value;
  50.           secondArgIsInteger = (value > 0.0) && value == Math.Floor(value);
  51.         }
  52.       }
  53.  
  54.       if (functionIsCalledPow && firstArgIsIdentifier && secondArgIsInteger)
  55.         consumer.AddHighlighting(new IntPowerHighlighting(element, power),
  56.           element.GetDocumentRange(), element.GetContainingFile());
  57.     }
  58.   }
  59.  
  60.   [StaticSeverityHighlighting(Severity.WARNING, CSharpLanguage.Name)]
  61.   public class IntPowerHighlighting : IHighlighting
  62.   {
  63.     public IInvocationExpression Expression { get; private set; }
  64.     public int Power { get; private set; }
  65.  
  66.     public IntPowerHighlighting(IInvocationExpression expression, int power)
  67.     {
  68.       Expression = expression;
  69.       Power = power;
  70.     }
  71.  
  72.     public bool IsValid()
  73.     {
  74.       return Expression != null && Expression.IsValid();
  75.     }
  76.  
  77.     public string ToolTip { get { return "Inefficient use of integer-based power"; } }
  78.     public string ErrorStripeToolTip { get { return ToolTip; } }
  79.     public int NavigationOffsetPatch { get { return 0; } }
  80.   }
  81.  
  82.   [QuickFix]
  83.   public class IntPowerInliningFix : BulbItemImpl, IQuickFix
  84.   {
  85.     private readonly IntPowerHighlighting highlighting;
  86.  
  87.     public IntPowerInliningFix(IntPowerHighlighting highlighting)
  88.     {
  89.       this.highlighting = highlighting;
  90.     }
  91.  
  92.     protected override Action<ITextControl> ExecutePsiTransaction(ISolution solution, IProgressIndicator progress)
  93.     {
  94.       var arg = highlighting.Expression.Arguments[0];
  95.       var factory = CSharpElementFactory.GetInstance(highlighting.Expression.GetPsiModule());
  96.       var replacement = factory.CreateExpression(
  97.         Enumerable.Range(0, highlighting.Power).Select(i => "$0").Join("*"), arg.Value);
  98.  
  99.       ModificationUtil.ReplaceChild(highlighting.Expression, replacement);
  100.       return null;
  101.     }
  102.  
  103.     public override string Text
  104.     {
  105.       get { return "Inline integer power"; }
  106.     }
  107.  
  108.     public bool IsAvailable(IUserDataHolder cache)
  109.     {
  110.       int power = highlighting.Power;
  111.       return power == 2 || power == 3;
  112.     }
  113.   }
  114. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement