{"id":70649,"date":"2017-04-25T16:32:32","date_gmt":"2017-04-25T16:32:32","guid":{"rendered":"https:\/\/www.simple-talk.com\/?p=70649"},"modified":"2021-06-03T16:47:01","modified_gmt":"2021-06-03T16:47:01","slug":"visual-lexicon-linq","status":"publish","type":"post","link":"https:\/\/www.red-gate.com\/simple-talk\/development\/dotnet-development\/visual-lexicon-linq\/","title":{"rendered":"A Visual Lexicon of LINQ"},"content":{"rendered":"<div style=\"columns: 3;\">\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#aggregate\">Aggregate<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#aggregate-count\">Count<\/a><\/li>\n<li><a href=\"#aggregate-longcount\">LongCount<\/a><\/li>\n<li><a href=\"#aggregate-sum\">Sum<\/a><\/li>\n<li><a href=\"#aggregate-averages\">Averages<\/a><\/li>\n<li><a href=\"#aggregate-max\">Max<\/a><\/li>\n<li><a href=\"#aggregate-min\">Min<\/a><\/li>\n<li><a href=\"#aggregate-aggregate\">Aggregate<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#conversion\">Conversion<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#conversion-cast\">Cast<\/a><\/li>\n<li><a href=\"#conversion-oftype\">OfType<\/a><\/li>\n<li><a href=\"#conversion-toarray\">ToArray<\/a><\/li>\n<li><a href=\"#conversion-tolist\">ToList<\/a><\/li>\n<li><a href=\"#conversion-todictionary\">ToDictionary<\/a><\/li>\n<li><a href=\"#conversion-tolookup\">ToLookup<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#elements\">Elements<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#elements-first\">First<\/a><\/li>\n<li><a href=\"#elements-firstordefault\">FirstOrDefault<\/a><\/li>\n<li><a href=\"#elements-last\">Last<\/a><\/li>\n<li><a href=\"#elements-lastordefault\">LastOrDefault<\/a><\/li>\n<li><a href=\"#elements-elementat\">ElementAt<\/a><\/li>\n<li><a href=\"#elements-elementatordefault\">ElementAtOrDefault<\/a><\/li>\n<li><a href=\"#elements-single\">Single<\/a><\/li>\n<li><a href=\"#elements-singleordefault\">SingleOrDefault<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#generation\">Generation<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#generation-range\">Range<\/a><\/li>\n<li><a href=\"#generation-repeat\">Repeat<\/a><\/li>\n<li><a href=\"#generation-empty\">Empty<\/a><\/li>\n<li><a href=\"#generation-defaultifempty\">DefaultIfEmpty<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#grouping\">Grouping<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#grouping-groupby\">GroupBy<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#join\">Join<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#join-crossjoin\">CrossJoin<\/a><\/li>\n<li><a href=\"#join-groupjoin\">GroupJoin<\/a><\/li>\n<li><a href=\"#join-concat\">Concat<\/a><\/li>\n<li><a href=\"#join-zip\">Zip<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#ordering\">Ordering<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#ordering-orderby\">OrderBy<\/a><\/li>\n<li><a href=\"#ordering-orderbydescending\">OrderByDescending<\/a><\/li>\n<li><a href=\"#ordering-thenby\">ThenBy<\/a><\/li>\n<li><a href=\"#ordering-thenbydescending\">ThenByDescending<\/a><\/li>\n<li><a href=\"#ordering-reverse\">Reverse<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#partitioning\">Partitioning<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#partitioning-take\">Take<\/a><\/li>\n<li><a href=\"#partitioning-skip\">Skip<\/a><\/li>\n<li><a href=\"#partitioning-takewhile\">TakeWhile<\/a><\/li>\n<li><a href=\"#partitioning-skipwhile\">SkipWhile<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#projection\">Projection<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#projection-select\">Select<\/a><\/li>\n<li><a href=\"#projection-selectmany\">SelectMany<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#quantifiers\">Quantifiers<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#quantifiers-any\">Any<\/a><\/li>\n<li><a href=\"#quantifiers-all\">All<\/a><\/li>\n<li><a href=\"#quantifiers-contains\">Contains<\/a><\/li>\n<li><a href=\"#quantifiers-sequenceequal\">SequenceEqual<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#restriction\">Restriction (Filtering)<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#restriction-where\">Where<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#sets\">Sets<\/a>\n<ul style=\"margin-bottom: 0; line-height: 20px;\">\n<li><a href=\"#sets-distinct\">Distinct<\/a><\/li>\n<li><a href=\"#sets-union\">Union<\/a><\/li>\n<li><a href=\"#sets-intersection\">Intersection<\/a><\/li>\n<li><a href=\"#sets-except\">Except<\/a><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"#conclusion\">Conclusion<\/a><\/li>\n<\/ul>\n<\/div>\n<p>&nbsp;<\/p>\n<p>Microsoft\u2019s Language-Integrated Query (LINQ) \u201cintroduces standard, easily-learned patterns for querying and updating data\u201d to quote <a href=\"https:\/\/msdn.microsoft.com\/en-us\/library\/mt693024.aspx\">MSDN<\/a>. Or does it? Something purportedly so easy should not need quite so many reference pages in MSDN. Yes, I\u2019m playing devil\u2019s advocate a bit here, as there is more to LINQ than just writing the queries, depending on what type of LINQ provider you need. When it comes to learning the LINQ patterns themselves, though, learning-by-example is likely the quickest route to mastery. Microsoft\u2019s venerable <a href=\"https:\/\/code.msdn.microsoft.com\/101-LINQ-Samples-3fb9811b\">101 LINQ Samples<\/a> page is a good start, though the examples there favor the use of query syntax. If you prefer lambda syntax, <a href=\"http:\/\/linq101.nilzorblog.com\/linq101-lambda.php\">LINQ 101 Samples &#8211; Lambda Style<\/a> provides a \u201ctranslation\u201d. Both of those resources, though helpful, feel somewhat dated. The simply named <a href=\"http:\/\/linqsamples.com\/\">LINQ Samples<\/a>, on the other hand, provides a much better user experience for navigating around the set of LINQ operators. Those are all good resources as far as they go but they are all <em>text<\/em>! When it comes to understanding a LINQ operator quickly, I submit that you can grasp it much faster with a <em>picture<\/em>.<\/p>\n<p>As an example, consider the following chunk of code. It computes student grade averages for each department then restricts the list to just those students whose grade is higher than their department\u2019s average. Immediately below the code is a visualization of the restriction step\u2014the LINQ <code>where<\/code> operator in the code. On the left you see the list of all students in a department, each marked with either a green checkmark (indicating a student is included) or a red X (indicating a student is excluded). On the right, that list is pruned down to students with grades exceeding 44.8 in this case. Between them you see light grey connecting lines showing how the students flow from the left to the right.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"384\" class=\"wp-image-70823\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-208.png\" \/><\/p>\n<p>This visualization is a screen shot of <a href=\"https:\/\/oz-code.com\/\">OzCode<\/a>, a Visual Studio extension that provides some impressive debugging aids. This image, as mentioned, illustrates the <code>where<\/code> operator. As you might suspect, you can click on the different operators at the top (<code>from<\/code>, <code>let<\/code>, <code>from<\/code>, <code>where<\/code>, or <code>select<\/code>) to see the input-to-output data flow for each operator.<\/p>\n<p>This article is a visual index of all LINQ operators based on such OzCode renderings, which gives you an immediate, intuitive grasp of a given operator. For most entries, OzCode renderings are used unaltered, but for a small number I have enhanced the illustrations to make it even more clear what a given operator is doing. (Many of the code fragments come from Microsoft\u2019s <a href=\"https:\/\/code.msdn.microsoft.com\/101-LINQ-Samples-3fb9811b\">101 LINQ Samples<\/a> page or from the MSDN reference page <a href=\"https:\/\/msdn.microsoft.com\/en-us\/library\/system.linq.enumerable_methods(v=vs.110).aspx\">Enumerable Methods<\/a>. )<\/p>\n<p>Most examples are shown using lambda syntax because all LINQ operators are available with lambda syntax while only a small number of them exist for query syntax. In fact, take a <a href=\"https:\/\/www.simple-talk.com\/dotnet\/net-development\/visual-lexicon-linq-wallchart\/\">look at the accompanying wallchart<\/a> to see at a glance which ones are available in query syntax, along with other key properties of all the LINQ operators, including which operators use deferred execution, how much of a sequence a given operator actually consumes, and more. Click to download the wallchart here:<\/p>\n<p><a href=\"https:\/\/www.simple-talk.com\/wp-content\/uploads\/2017\/04\/Visual-LINQ-wallchart.pdf\"><img loading=\"lazy\" decoding=\"async\" width=\"644\" height=\"377\" class=\"wp-image-70824\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/c-users-ms-appdata-local-temp-snaghtmlc57c30c-png-3.png\" alt=\"C:\\Users\\ms\\AppData\\Local\\Temp\\SNAGHTMLc57c30c.PNG\" \/><\/a><\/p>\n<div class=\"note\">\n<p>If you want to leverage all the power of LINQ from your PowerShell code as well, see the third part in this series, <a href=\"https:\/\/www.simple-talk.com\/dotnet\/net-framework\/high-performance-powershell-linq\/\">High Performance PowerShell with LINQ<\/a>.<\/p>\n<\/div>\n<h2 id=\"aggregate\">Aggregate<\/h2>\n<h3 id=\"aggregate-count\">Count<\/h3>\n<p>Returns the number of elements in a sequence. When the result is expected to be greater than <code>Int32.MaxValue()<\/code>, use <strong>LongCount<\/strong>.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"148\" class=\"wp-image-70825\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-209.png\" \/><\/p>\n<p>If you specify an optional condition, <strong>Count<\/strong> returns the number of elements in a sequence that satisfies that condition.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"210\" class=\"wp-image-70826\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-210.png\" \/><\/p>\n<h3 id=\"aggregate-longcount\">LongCount<\/h3>\n<p>Returns <em>as an Int64<\/em> the number of elements in a sequence. Use <strong>LongCount<\/strong> rather than <strong>Count<\/strong> when the result is expected to be greater than <code>Int32.MaxValue()<\/code>. <strong>LongCount<\/strong>, like <strong>Count<\/strong>, allows an optional condition.<\/p>\n<p>Visualizes identically to <strong>Count<\/strong>.<\/p>\n<h3 id=\"aggregate-sum\">Sum<\/h3>\n<p>Computes the <em>sum<\/em> of a sequence of values.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"192\" class=\"wp-image-70827\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-211.png\" \/><\/p>\n<p>If you specify an optional transformation function, <strong>Sum<\/strong> computes the sum of a sequence of values after applying that transformation on each element. Note the additional column of values as compared to the straight <strong>Sum<\/strong> method above. Those values, adjacent to the input sequence values, reveal the transformed values.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"192\" class=\"wp-image-70828\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-212.png\" \/><\/p>\n<h3 id=\"aggregate-averages\">Average<\/h3>\n<p>Computes the <em>average<\/em> of a sequence of values. If you specify an optional transformation function, <strong>Average<\/strong> computes the average of a sequence of values after applying that transformation on each element.<\/p>\n<p>Visualizes identically to <strong>Sum<\/strong>.<\/p>\n<h3 id=\"aggregate-max\">Max<\/h3>\n<p>Returns the <em>maximum<\/em> value in a sequence. If you specify an optional transformation function, <strong>Max <\/strong>returns the maximum value in a sequence after applying that transformation on each element. (See the <strong>Min<\/strong> method for an example with the transformation function.)<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"144\" class=\"wp-image-70829\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-213.png\" \/><\/p>\n<h3 id=\"aggregate-min\">Min<\/h3>\n<p>Returns the <em>minimum<\/em> value in a sequence. If you specify an optional transformation function, <strong>Min<\/strong> returns the minimum value in a sequence after applying that transformation on each element, as shown here. Note the additional column of values as compared to the <strong>Max<\/strong> method. Those values, adjacent to the input sequence values, reveal the transformed values.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"144\" class=\"wp-image-70830\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-214.png\" \/><\/p>\n<h3 id=\"aggregate-aggregate\">Aggregate<\/h3>\n<p>Applies an accumulator function over a sequence. Note the additional column of values adjacent to the input sequence values, revealing the accumulated value with every element. You specify a two-argument function to perform an arbitrary aggregation function of your choice. The first parameter is the accumulated results so far, which is initialized to the default value for the element type (in this case, zero), and the second parameter is the sequence element.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"174\" class=\"wp-image-70831\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-215.png\" \/><\/p>\n<p>If you specify an initial seed, <strong>Aggregate<\/strong> applies an accumulator function over a sequence with that initial seed value. While the seed could just be (depending on your needs) some constant integer or constant string, it could also create an object that your accumulator function will call methods against, as shown next. Here a <code>StringBuilder<\/code> is created that is used in each step of the aggregation. Note the additional column of values adjacent to the input sequence values, revealing the accumulated value with every element.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"627\" height=\"160\" class=\"wp-image-70832\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-216.png\" \/><\/p>\n<h2 id=\"conversion\">Conversion<\/h2>\n<h3 id=\"conversion-cast\">Cast<\/h3>\n<p>Casts the elements of an <code>IEnumerable<\/code> to the specified type, effectively converting <code>IEnumerable<\/code> to <code>IEnumerable&lt;T&gt;<\/code>, which then makes the sequence amenable to further LINQ operations. The example shows an <code>ArrayList<\/code>, which is not a generic type, converted to generic with <strong>Cast<\/strong>.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"175\" class=\"wp-image-70833\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-217.png\" \/><\/p>\n<h3 id=\"conversion-oftype\">OfType<\/h3>\n<p>Filters the elements of an <code>IEnumerable<\/code> based on a specified type (similar to <strong>Where<\/strong>). Note that, despite what the OzCode visualization here leads you to believe by rendering \u201c4.0\u201d as just \u201c4\u201d, <strong>OfType<\/strong> does <em>not<\/em> include types that are <em>implicitly<\/em> castable, only exact type matches. That\u2019s why 4.0 passes the filter but 3 does not.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"171\" class=\"wp-image-70834\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-218.png\" \/><\/p>\n<h3 id=\"conversion-toarray\">ToArray<\/h3>\n<p>Creates an array from an <code>IEnumerable&lt;T&gt;<\/code>. Note that execution of this LINQ query is deferred through the <strong>Select<\/strong> step, but the <strong>ToArray<\/strong> method is immediately executed, causing the entire query to execute.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"155\" class=\"wp-image-70835\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-219.png\" \/><\/p>\n<h3 id=\"conversion-tolist\">ToList<\/h3>\n<p>Creates a <code>List&lt;T&gt;<\/code> from an <code>IEnumerable&lt;T&gt;<\/code>. Note that execution of this LINQ query is deferred through the <strong>Select<\/strong> step, but the <strong>ToList<\/strong> method is immediately executed, causing the entire query to execute.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"145\" class=\"wp-image-70836\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-220.png\" \/><\/p>\n<h3 id=\"conversion-todictionary\">ToDictionary<\/h3>\n<p>Creates a <code>Dictionary&lt;TKey,\u2002TValue&gt;<\/code> from an <code>IEnumerable&lt;T&gt;<\/code> according to a specified key selector function (<code>g =&gt; g.Key<\/code> in this example). The value of the dictionary entry (<code>TValue<\/code>) is just the current input element from the sequence unless you specify the optional element selector function, in which case the value is computed with that function. The example here uses <code>g =&gt; g.ToList()<\/code> for the element selector function, generating a <code>List&lt;string&gt;<\/code> for each dictionary entry.<\/p>\n<p>A <code>Dictionary<\/code> is a one-to-one map, and is editable after creation. Querying on a non-existent key throws an exception. Contrast this with <strong>ToLookup<\/strong>.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"314\" class=\"wp-image-70837\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-221.png\" \/><\/p>\n<h3 id=\"conversion-tolookup\">ToLookup<\/h3>\n<p>Creates a <code>Lookup&lt;TKey,\u2002TElement&gt;<\/code> from an <code>IEnumerable&lt;T&gt;<\/code> according to a specified key selector function (<code>c =&gt;<\/code> <code>c.Length<\/code> in this example\u2014its values appear in the second column). If the optional element selector function is also provided, the value of the lookup element (<code>TElement<\/code>) is computed with that function (not used in this example; see <strong>ToDictionary<\/strong> for a sample usage).<\/p>\n<p>A <code>Lookup<\/code> is a one-to-many map that is <em>not<\/em> mutable after creation. Querying on a non-existent key returns an empty sequence. Contrast thiswith <strong>ToDictionary<\/strong>.<\/p>\n<p>Note that <code>Lookup&lt;TKey,TValue&gt;<\/code> is roughly comparable to a <code>Dictionary&lt;TKey,IEnumerable&lt;TValue&gt;&gt;<\/code>. (Thanks to Mark Gravell for this tip on <a href=\"http:\/\/stackoverflow.com\/a\/5659080\/115690\">Stack Overflow<\/a>.) Compare the results view here with that for <strong>ToDictionary<\/strong> to see the differences.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"227\" class=\"wp-image-70838\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-222.png\" \/><\/p>\n<h2 id=\"elements\">Elements<\/h2>\n<h3 id=\"elements-first\">First<\/h3>\n<p>Returns the first element of a sequence. Throws an exception if the sequence contains no elements. Note that evaluation stops at the first element in the sequence; the remainder of the sequence is not evaluated.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"127\" class=\"wp-image-70839\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-223.png\" \/><\/p>\n<p>If you specify an optional condition, <strong>First<\/strong> returns the first element in a sequence that satisfies that condition. Throws an exception if no elements satisfy the condition. Note that evaluation stops at the first element satisfying the condition in the sequence; the remainder of the sequence is not evaluated.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"153\" class=\"wp-image-70840\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-224.png\" \/><\/p>\n<h3 id=\"elements-firstordefault\">FirstOrDefault<\/h3>\n<p>Returns the <em>first<\/em> element of a sequence, or a default value if the sequence contains no elements. Note that evaluation stops at the first element in the sequence; the remainder of the sequence is not evaluated.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"166\" class=\"wp-image-70841\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-225.png\" \/><\/p>\n<p>If you specify an optional condition, <strong>FirstOrDefault<\/strong> returns the first element in a sequence that satisfies that condition, or a default value if the sequence contains no elements. Note that evaluation stops at the first element satisfying the condition in the sequence; the remainder of the sequence is not evaluated.<\/p>\n<h3 id=\"elements-last\">Last<\/h3>\n<p>Returns the <em>last<\/em> element of a sequence. Throws an exception if the sequence contains no elements. The entire sequence must be evaluated to get to the last element.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"245\" class=\"wp-image-70842\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-226.png\" \/><\/p>\n<p>If you specify an optional condition, <strong>Last<\/strong> returns the last element of a sequence that satisfies that condition. Throws an exception if the sequence contains no elements. The entire sequence must be evaluated to identify the target element, even if it ends up not being the actual last one in the sequence.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"169\" class=\"wp-image-70843\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-227.png\" \/><\/p>\n<h3 id=\"elements-lastordefault\">LastOrDefault<\/h3>\n<p>Returns the <em>last<\/em> element of a sequence, or a default value if the sequence contains no elements. The entire sequence must be evaluated to get to the last element.<\/p>\n<p>If you specify an optional condition, <strong>LastOrDefault<\/strong> returns the last element of a sequence that satisfies that condition, or a default value if the sequence contains no elements. The entire sequence must be evaluated to identify the target element, even if it ends up not being the actual last one in the sequence.<\/p>\n<p>Visualizes identically to <strong>FirstOrDefault<\/strong>.<\/p>\n<h3 id=\"elements-elementat\">ElementAt<\/h3>\n<p>Returns the element at a specified index in a sequence. Throws an exception if the index is out of range.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"162\" class=\"wp-image-70844\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-228.png\" \/><\/p>\n<h3 id=\"elements-elementatordefault\">ElementAtOrDefault<\/h3>\n<p>Returns the element at a specified index in a sequence, or a default value if the index is out of range.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"173\" class=\"wp-image-70845\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-229.png\" \/><\/p>\n<h3 id=\"elements-single\">Single<\/h3>\n<p>Returns the <em>only<\/em> element of a sequence. Throws an exception if the sequence contains more than one element.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"185\" class=\"wp-image-70846\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-230.png\" \/><\/p>\n<p>If you specify an optional condition, <strong>Single<\/strong> returns the only element in a sequence that satisfies that condition. Throws an exception if either no elements or more than one element satisfy the condition.<\/p>\n<h3 id=\"elements-singleordefault\">SingleOrDefault<\/h3>\n<p>Returns the <em>only<\/em> element of a sequence or a default value if the sequence is empty. Throws an exception if the sequence contains more than one element.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"131\" class=\"wp-image-70847\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-231.png\" \/><\/p>\n<p>If you specify an optional condition, <strong>SingleOrDefault<\/strong> returns the only element in a sequence that satisfies that condition, or a default value if the sequence is empty. Throws an exception if the sequence contains more than one element.<\/p>\n<h2 id=\"generation\">Generation<\/h2>\n<h3 id=\"generation-range\">Range<\/h3>\n<p>Generates a sequence of integral numbers within a specified range.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"173\" class=\"wp-image-70848\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-232.png\" \/><\/p>\n<h3 id=\"generation-repeat\">Repeat<\/h3>\n<p>Generates a sequence that contains a repeated value a specified number of times.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"162\" class=\"wp-image-70849\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-233.png\" \/><\/p>\n<h3 id=\"generation-empty\">Empty<\/h3>\n<p>Returns an empty <code>IEnumerable&lt;T&gt;<\/code> that has the specified type argument.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"118\" class=\"wp-image-70850\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-234.png\" \/><\/p>\n<h3 id=\"generation-defaultifempty\">DefaultIfEmpty<\/h3>\n<p>Returns the default value of the sequence\u2019s elements (or, if a type parameter is explicitly specified, that type\u2019s default value) in a singleton collection if the sequence is empty.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"152\" class=\"wp-image-70851\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-235.png\" \/><\/p>\n<p>If the sequence is non-empty, simply returns the original sequence.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"163\" class=\"wp-image-70852\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-236.png\" \/><\/p>\n<h2 id=\"grouping\">Grouping<\/h2>\n<h3 id=\"grouping-groupby\">GroupBy<\/h3>\n<p>Groups the elements of a sequence according to a specified key selector function (<code>pet =&gt;<\/code> <code>pet.Age<\/code> in this example\u2014its values appear in the second column). In the result, the second group is expanded to show its contents, containing 2 members of age 4. Notice that the elements of the group are objects of the original type, <code>Pet<\/code>.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"272\" class=\"wp-image-70853\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-237.png\" \/><\/p>\n<p>If you specify an optional projection function, <strong>GroupBy<\/strong> further projects the elements for each group with that function (<code>pet =&gt;<\/code> <code>pet.Name<\/code> in this next example). In the result, the second group is expanded to show its contents, containing 2 members of age 4. Notice that the elements of the group are now comprised of just the projected property, the pet\u2019s name.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"240\" class=\"wp-image-70854\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-238.png\" \/><\/p>\n<h2 id=\"join\">Join<\/h2>\n<h3 id=\"join-crossjoin\">Cross Join<\/h3>\n<p>Correlates the elements of two sequences based on matching keys. If the first sequence has no corresponding elements in the second sequence, it is <em>not<\/em> represented in the result. <strong>Join<\/strong> is equivalent to an inner join in SQL.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"526\" class=\"wp-image-70855\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-239.png\" \/><\/p>\n<h3 id=\"join-groupjoin\">Group Join<\/h3>\n<p>Correlates the elements of two sequences based on equality of keys and groups the results. If the first sequence has no corresponding elements in the second sequence, it is <em>still<\/em> represented in the result but its group contains no members. In the example, notice that user Chuck (id=4) has no books associated with him. <strong>Group Join<\/strong> is equivalent to a left outer join in SQL.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"582\" height=\"660\" class=\"wp-image-70856\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-240.png\" \/><\/p>\n<h3 id=\"join-concat\">Concat<\/h3>\n<p>Concatenates two sequences into a single sequence; further LINQ operations would then operate on the new, combined sequence.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"195\" class=\"wp-image-70857\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-241.png\" \/><\/p>\n<h3 id=\"join-zip\">Zip<\/h3>\n<p>Applies a specified function to the corresponding elements of two sequences, producing a new sequence of the results. If the first sequence is longer than the second, one element past the common length will be evaluated (\u201cd\u201d in the illustration) at which point a determination is made that the second sequence has been consumed, and further evaluation stops (so \u201ce\u201d is not evaluated). If the second sequence is longer than the first, its extra values will not be evaluated at all. Note that \u201czip\u201d in this context has nothing to do with zip archives!<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"189\" class=\"wp-image-70858\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-242.png\" \/><\/p>\n<h2 id=\"ordering\">Ordering<\/h2>\n<h3 id=\"ordering-orderby\">OrderBy<\/h3>\n<p>Sorts the elements of a sequence in <em>ascending<\/em> order according to a key selector function. (<code>i =&gt;<\/code> <code>i.Count<\/code>) in this example\u2014its values appear in the second column).<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"246\" class=\"wp-image-70859\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-243.png\" \/><\/p>\n<h3 id=\"ordering-orderbydescending\">OrderByDescending<\/h3>\n<p>Sorts the elements of a sequence in <em>descending<\/em> order according to a key selector function.<\/p>\n<p>Visualizes identically to <strong>OrderBy<\/strong>.<\/p>\n<h3 id=\"ordering-thenby\">ThenBy<\/h3>\n<p>Performs a <em>subsequent<\/em> ordering of the elements in a sequence in <em>ascending<\/em> order according to a key selector function (<code>d =&gt;<\/code> <code>d.Month<\/code> in this example\u2014its values appear in the second column). Note that unlike most other LINQ operators, which accept an <code>IEnumerable&lt;T&gt; <\/code>input, <strong>ThenBy<\/strong> accepts an <code>IOrderedEnumerable&lt;T&gt;<\/code> input\u2014which happens to be the output of <strong>OrderBy<\/strong>.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"229\" class=\"wp-image-70860\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-244.png\" \/><\/p>\n<h3 id=\"ordering-thenbydescending\">ThenByDescending<\/h3>\n<p>Performs a <em>subsequent<\/em> ordering of the elements in a sequence in <em>descending<\/em> order according to a key selector function. Note that unlike most other LINQ operators, which accept an <code>IEnumerable&lt;T&gt; <\/code>input, <strong>ThenBy<\/strong> accepts an <code>IOrderedEnumerable&lt;T&gt;<\/code> input\u2014which happens to be the output of <strong>OrderBy<\/strong>.<\/p>\n<p>Visualizes identically to <strong>ThenBy<\/strong>.<\/p>\n<h3 id=\"ordering-reverse\">Reverse<\/h3>\n<p>Inverts the order of the elements in a sequence.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"184\" class=\"wp-image-70861\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-245.png\" \/><\/p>\n<h2 id=\"partitioning\">Partitioning<\/h2>\n<h3 id=\"partitioning-take\">Take<\/h3>\n<p>Returns a specified number of elements from the start of a sequence. Evaluation of the sequence stops after that as no further elements are needed.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"168\" class=\"wp-image-70862\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-246.png\" \/><\/p>\n<h3 id=\"partitioning-skip\">Skip<\/h3>\n<p>Bypasses a specified number of elements in a sequence and then returns the remaining elements.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"624\" height=\"210\" class=\"wp-image-70863\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-247.png\" \/><\/p>\n<h3 id=\"partitioning-takewhile\">TakeWhile<\/h3>\n<p>Returns elements from the start of a sequence as long as a specified condition is true. Evaluation of the sequence stops after that as no further elements are needed.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"195\" class=\"wp-image-70864\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-248.png\" \/><\/p>\n<h3 id=\"partitioning-skipwhile\">SkipWhile<\/h3>\n<p>Bypasses elements in a sequence as long as a specified condition is true and then returns the remaining elements.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"238\" class=\"wp-image-70865\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-249.png\" \/><\/p>\n<h2 id=\"projection\">Projection<\/h2>\n<h3 id=\"projection-select\">Select<\/h3>\n<p>Applies a specified transformation to each element of a sequence; this transformation is generally referred to as \u201cprojection\u201d. Often you might project into a new object that is a subset of the original object, essentially discarding unneeded properties. In the illustration, just one property of the <code>DateTime<\/code> object is needed for further processing so the sequence is transformed to a new sequence with just the <code>DayOfYear<\/code> property. But you are not limited to just a subset; you can combine values from different sequences (see the <strong>Cross Join<\/strong> example) or you can even transform elements (see the <strong>Repeat<\/strong> example).<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"192\" class=\"wp-image-70866\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-250.png\" \/><\/p>\n<h3 id=\"projection-selectmany\">SelectMany<\/h3>\n<p>Projects each element of a sequence to an <code>IEnumerable&lt;T&gt; <\/code>and flattens the resulting sequences into a single sequence. If, in the illustration, <code>Select<\/code> had been used instead of <code>SelectMany<\/code>, each element of the result would be a list of <code>User<\/code> objects (i.e. a list of string <em>arrays<\/em>) rather than a list of <em>strings<\/em>, as shown, and the result would be just a 2-element list rather than a 6-element list.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"276\" class=\"wp-image-70867\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-251.png\" \/><\/p>\n<h2 id=\"quantifiers\">Quantifiers<\/h2>\n<h3 id=\"quantifiers-any\">Any<\/h3>\n<p>Determines whether <em>any<\/em> element of a sequence (i.e. at least one element) satisfies a condition. All elements of the sequence need to be evaluated to provide a <code>false<\/code> result (first figure). However, if at any time during evaluating the sequence an element evaluates to <code>true<\/code>, the sequence evaluation stops at that element (second figure). Of course, if <em>only<\/em> the last element satisfies the condition, all elements will need to be evaluated and <code>true<\/code> will be returned.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"159\" class=\"wp-image-70868\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-252.png\" \/><\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"130\" class=\"wp-image-70869\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-253.png\" \/><\/p>\n<h3 id=\"quantifiers-all\">All<\/h3>\n<p>Determines whether <em>all<\/em> elements of a sequence satisfy a condition. All elements of the sequence need to be evaluated to provide a <code>true<\/code> result (first figure). However, if at any time during evaluating the sequence an element evaluates to <code>false<\/code>, the sequence evaluation stops at that element (second figure). Of course, if <em>only<\/em> the last element fails to satisfy the condition, all elements will need to be evaluated and <code>false<\/code> will be returned.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"173\" class=\"wp-image-70870\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-254.png\" \/><\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"156\" class=\"wp-image-70871\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-255.png\" \/><\/p>\n<h3 id=\"quantifiers-contains\">Contains<\/h3>\n<p>Determines whether a sequence contains a specified element. The sequence may, of course, contain objects of an arbitrary type. In the case of strings, however, note that this method matches against each element in its entirety. Contrast this to the <code>string<\/code> method <code>Contains<\/code> that determines whether a string matches against a substring. (See the example for <strong>Any<\/strong> .)<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"145\" class=\"wp-image-70872\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-256.png\" \/><\/p>\n<h3 id=\"quantifiers-sequenceequal\">SequenceEqual<\/h3>\n<p>Determines whether two sequences are equal; specifically, if the two sequences contain the <em>same<\/em> elements in the <em>same<\/em> order. When dealing with value types, as in the illustration, the use is intuitive: the lists differ at the third position so a determination has been made that they are different, and no further elements of the sequence need to be evaluated.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"166\" class=\"wp-image-70873\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-257.png\" \/><\/p>\n<p>But if you use reference types, the elements are matched with <em>reference equality<\/em>; they need to be the actual, same object, not just objects with all the same property values. If you use different reference objects then the sequences are not equal:<\/p>\n<pre class=\"theme:ssms2012-simple-talk lang:tsql decode:true\">var pets1 = new List\r\n{\r\n    new Pet { Age = 5, Name = \"fido\" }\r\n};\r\nvar pets2 = new List\r\n{\r\n    new Pet { Age = 5, Name = \"fido\" }\r\n};\r\nvar result = pets1.SequenceEqual(pets2); \/\/ evaluates to false!\r\n<\/pre>\n<p>By using the same actual object, then the sequences are considered equal:<\/p>\n<pre class=\"theme:ssms2012-simple-talk lang:tsql decode:true\">var\u00a0pet\u00a0=\u00a0new\u00a0Pet\u00a0{\u00a0Age\u00a0=\u00a05,\u00a0Name\u00a0=\u00a0\"fido\"\u00a0};\r\nvar\u00a0pets1\u00a0=\u00a0new\u00a0List&lt;Pet&gt;\r\n{\r\n  \u00a0\u00a0pet\r\n};\r\nvar\u00a0pets2\u00a0=\u00a0new\u00a0List&lt;Pet&gt;\r\n{\r\n  \u00a0\u00a0pet\r\n};\r\nvar\u00a0result\u00a0=\u00a0pets1.SequenceEqual(pets2);\u00a0\/\/\u00a0evaluates\u00a0to\u00a0true!<\/pre>\n<p>Note that you can modify this behavior of using reference equality by either having the type implement <code>IEquatable&lt;T&gt;<\/code>, or using an overload that accepts an <code>IEqualityComparer<\/code>. Then you tailor the behavior as you wish.<\/p>\n<h2 id=\"restriction\">Restriction (Filtering)<\/h2>\n<h3 id=\"restriction-where\">Where<\/h3>\n<p>Filters a sequence of values based on a predicate.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"202\" class=\"wp-image-70874\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-258.png\" \/><\/p>\n<h2 id=\"sets\">Sets<\/h2>\n<h3 id=\"sets-distinct\">Distinct<\/h3>\n<p>Returns distinct elements from a sequence. Note that the sequence does <em>not<\/em> need to be sorted.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"174\" class=\"wp-image-70875\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-259.png\" \/><\/p>\n<h3 id=\"sets-union\">Union<\/h3>\n<p>Produces the set union of two sequences. Includes elements in both sequences but without duplication.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"226\" class=\"wp-image-70876\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-260.png\" \/><\/p>\n<h3 id=\"sets-intersection\">Intersection<\/h3>\n<p>Produces the set intersection of two sequences. Just those elements that exist in both sequences appear in the result.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"198\" class=\"wp-image-70877\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-261.png\" \/><\/p>\n<h3 id=\"sets-except\">Except<\/h3>\n<p>Produces the set difference of one sequence with a second sequence. Just those elements that exist in the first sequence and do <em>not<\/em> exist in the second sequence appear in the result.<\/p>\n<p><a href=\"https:\/\/www.simple-talk.com\/wp-content\/uploads\/2017\/04\/Visual-LINQ-wallchart.pdf\"><img loading=\"lazy\" decoding=\"async\" width=\"640\" height=\"210\" class=\"wp-image-70878\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-262.png\" \/><\/a><\/p>\n<h2 id=\"conclusion\">Conclusion<\/h2>\n<p>This article serves as a visual dictionary of LINQ operators showing not just code samples but a visualization of what each associated LINQ operator in the code is doing. But there\u2019s more! Accompanying this article is<a href=\"https:\/\/www.simple-talk.com\/dotnet\/net-development\/visual-lexicon-linq-wallchart\/\"> a handy wallchart<\/a> that condenses the information here even further, plus adds some more technical specs. For example, it shows you at a glance which operators use deferred execution and which use immediate execution. <a href=\"https:\/\/www.simple-talk.com\/wp-content\/plugins\/download-attachments\/includes\/download.php?id=70883\">Click here to download the PDF reference chart<\/a>:<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"644\" height=\"377\" class=\"wp-image-70879\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2017\/04\/word-image-263.png\" \/><\/p>\n","protected":false},"excerpt":{"rendered":"<p>LINQ is best learned from examples, but few LINQ resources supply, along with the code, pictures that illustrate what each associated LINQ operator in the code is doing. This article is a visual index of all LINQ operators, that explain clearly with code and illustrations what even the most arcane LINQ operators actually do. To increase your enlightenment, it is accompanied <a href=\"https:\/\/www.simple-talk.com\/dotnet\/net-development\/visual-lexicon-linq-wallchart\/\">with a reference chart <\/a>to provide even more detail. Michael Sorens is, with these two articles, determined to persuade you of the power of LINQ.&hellip;<\/p>\n","protected":false},"author":221868,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[143538],"tags":[4706],"coauthors":[6802],"class_list":["post-70649","post","type-post","status-publish","format-standard","hentry","category-dotnet-development","tag-linq"],"acf":[],"_links":{"self":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/70649","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/users\/221868"}],"replies":[{"embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/comments?post=70649"}],"version-history":[{"count":19,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/70649\/revisions"}],"predecessor-version":[{"id":91244,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/70649\/revisions\/91244"}],"wp:attachment":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/media?parent=70649"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/categories?post=70649"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/tags?post=70649"},{"taxonomy":"author","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/coauthors?post=70649"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}