-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathresharper-search-with-pattern.html
94 lines (76 loc) · 7.04 KB
/
resharper-search-with-pattern.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
<!DOCTYPE html>
<html lang="ru">
<head>
<title>tkirill's blog</title>
<meta charset="utf-8" />
<link rel="stylesheet" type="text/css" href="./theme/css/bootstrap/bootstrap.min.css" />
<link rel="stylesheet" type="text/css" href="./theme/css/blog.css" />
<script>
(function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){
(i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),
m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)
})(window,document,'script','//www.google-analytics.com/analytics.js','ga');
ga('create', 'UA-49219502-1', 'tkirill.org');
ga('send', 'pageview');
</script>
<link rel="stylesheet" type="text/css" href="./theme/css/pygments-friendly.css" />
</head>
<body>
<div class="container">
<div class="row">
<div class="col-md-12">
<h1><a href=".">tkirill's blog</a></h1>
</div>
</div>
<div class="row">
<div class="col-md-12">
<hr>
</div>
</div>
<div class="row">
<div class="col-md-8">
<p class="article-date">
Ср. 02 Апрель 2014
</p>
<h2>
<a href="./resharper-search-with-pattern.html" rel="bookmark" title="Permalink to Search with Pattern в ReSharper">Search with Pattern в ReSharper</a>
</h2>
<div class="article-content">
<p>Долгое время я ждал задачи, в которой получилось бы использовать Search with Pattern — многообещающую фичу ReSharper, которую по-русски я буду называть структурным поиском. В этом поиске используются шаблоны, которые похожи на регулярные выражения, только работающие в грамматике C#, то есть они оперируют идентификаторами, переменными, выражениями и другими структурами языка.</p>
<p>Например, пусть раньше в тестах для сравнения строк без учёта регистра использовался StringAssert:</p>
<div class="highlight"><pre><span></span><span class="n">StringAssert</span><span class="p">.</span><span class="n">AreEqualIgnoringCase</span><span class="p">(</span><span class="s">"2013.1.1"</span><span class="p">,</span> <span class="k">new</span> <span class="n">DateTime</span><span class="p">(</span><span class="m">2013</span><span class="p">,</span> <span class="m">1</span><span class="p">,</span> <span class="m">1</span><span class="p">).</span><span class="n">ToString</span><span class="p">(</span><span class="s">"yyyy.M.d"</span><span class="p">));</span>
<span class="c1">//...</span>
<span class="n">StringAssert</span><span class="p">.</span><span class="n">AreEqualIgnoringCase</span><span class="p">(</span><span class="s">"AA"</span><span class="p">+</span><span class="s">"bb"</span><span class="p">,</span> <span class="kt">string</span><span class="p">.</span><span class="n">Concat</span><span class="p">(</span><span class="s">"aa"</span><span class="p">,</span> <span class="s">"BB"</span><span class="p">));</span>
</pre></div>
<p>То есть, в качестве первого и второго аргументов могут передаваться произвольные выражения, а не только строковые литералы. Теперь представим, что в проекте поменялись соглашения и теперь все проверки принято записывать через Assert.That. Наш пример в новых соглашениях будет выглядеть так:</p>
<div class="highlight"><pre><span></span><span class="n">Assert</span><span class="p">.</span><span class="n">That</span><span class="p">(</span><span class="k">new</span> <span class="n">DateTime</span><span class="p">(</span><span class="m">2013</span><span class="p">,</span> <span class="m">1</span><span class="p">,</span> <span class="m">1</span><span class="p">).</span><span class="n">ToString</span><span class="p">(</span><span class="s">"yyyy.M.d"</span><span class="p">),</span> <span class="n">Is</span><span class="p">.</span><span class="n">EqualTo</span><span class="p">(</span><span class="s">"2013.1.1"</span><span class="p">).</span><span class="n">IgnoreCase</span><span class="p">);</span>
<span class="c1">//...</span>
<span class="n">Assert</span><span class="p">.</span><span class="n">That</span><span class="p">(</span><span class="kt">string</span><span class="p">.</span><span class="n">Concat</span><span class="p">(</span><span class="s">"aa"</span><span class="p">,</span> <span class="s">"BB"</span><span class="p">),</span> <span class="n">Is</span><span class="p">.</span><span class="n">EqualTo</span><span class="p">(</span><span class="s">"AA"</span> <span class="p">+</span> <span class="s">"bb"</span><span class="p">).</span><span class="n">IgnoreCase</span><span class="p">);</span>
</pre></div>
<p>Мы можем использовать структурный поиск для замены старого способа записи на новый. Выбрав пункт меню ReSharper -> Find -> Search with Pattern и нажав в открывшемся окне на Replace в верхнем правом углу мы приступаем к написанию шаблона.</p>
<p><img alt="ReSharper Search with Pattern window" src="./images/resharper-search-with-pattern/empty-search-with-pattern.png" title="ReSharper Search with Pattern window" /></p>
<p>Шаблон для поиска:</p>
<div class="highlight"><pre><span></span>StringAssert.AreEqualIgnoringCase($expected$, $actual$);
</pre></div>
<p>Шаблон для замены:</p>
<div class="highlight"><pre><span></span>Assert.That($actual$, Is.EqualTo($expected$).IgnoreCase);
</pre></div>
<p>expected и actual обозначают аргументы, мы задаём это явно в настройках placeholder:</p>
<p><img alt="Argument constraints in ReSharper Search with Pattern" src="./images/resharper-search-with-pattern/argument-constraint.png" title="Argument constraints in ReSharper Search with Pattern" /></p>
<p>Нам остаётся нажать Replace, остальное сделает ReSharper.</p>
</div>
</div>
</div>
<div class="row">
<div class="col-md-12">
<hr>
</div>
</div>
<div class="row">
<div class="col-md-12">
<p class="pelican-credits">Powered by <a href="http://docs.getpelican.com/">Pelican</a></p>
</div>
</div>
</div>
</body>
</html>