Skip to content

Commit

Permalink
Clarified the use of var (AV1520) and supplemented AV1707 (names) (#252)
Browse files Browse the repository at this point in the history
  • Loading branch information
bkoelman authored Feb 10, 2022
1 parent 9921575 commit f720261
Show file tree
Hide file tree
Showing 2 changed files with 25 additions and 13 deletions.
37 changes: 24 additions & 13 deletions _rules/1520.md
Original file line number Diff line number Diff line change
@@ -1,22 +1,33 @@
---
rule_id: 1520
rule_category: maintainability
title: Only use `var` when the type is very obvious
title: Only use `var` when the type is evident
severity: 1
---
Only use `var` as the result of a LINQ query, or if the type is very obvious from the same statement and using it would improve readability. So don't
Use `var` for anonymous types (typically resulting from a LINQ query), or if the type is [evident](https://www.jetbrains.com/help/resharper/2021.3/Using_var_Keyword_in_Declarations.html#use-var-when-evident-details).
Never use `var` for [built-in types](https://docs.microsoft.com/en-us/dotnet/csharp/language-reference/builtin-types/built-in-types).

// what type? int? uint? float?
var item = 3;
// Projection into anonymous type.
var largeOrders =
from order in dbContext.Orders
where order.Items.Count > 10 && order.TotalAmount > 1000
select new { order.Id, order.TotalAmount };

// Not obvious what base-class or interface to expect.
// Also difficult to refactor if you can't search for the class.
var myfoo = MyFactoryMethod.Create("arg");
// Built-in types.
bool isValid = true;
string phoneNumber = "(unavailable)";
uint pageSize = Math.Max(itemCount, MaxPageSize);

Instead, use `var` like this:
// Types are evident.
var customer = new Customer();
var invoice = Invoice.Create(customer.Id);
var user = sessionCache.Resolve<User>("[email protected]");
var subscribers = new List<Subscriber>();
var summary = shoppingBasket.ToOrderSummary();

var query = from order in orders where order.Items > 10 and order.TotalValue > 1000;
var repository = new RepositoryFactory.Get();
var list = new ReadOnlyCollection();

In all of three above examples it is clear what type to expect. For a more detailed rationale about the advantages and disadvantages of using `var`, read Eric Lippert's [Uses and misuses of implicit typing](https://docs.microsoft.com/en-us/archive/blogs/ericlippert/uses-and-misuses-of-implicit-typing).
// All other cases.
IQueryable<Order> recentOrders = ApplyFilter(order => order.CreatedAt > DateTime.Now.AddDays(-30));
LoggerMessage message = Compose(context);
ReadOnlySpan<string> key = ExtractKeyFromPair("[email protected]");
IDictionary<Category, Product> productsPerCategory =
shoppingBasket.Products.ToDictionary(product => product.Category);
1 change: 1 addition & 0 deletions _rules/1707.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,3 +7,4 @@ severity: 2
- Use functional names. For example, `GetLength` is a better name than `GetInt`.
- Don't use terms like `Enum`, `Class` or `Struct` in a name.
- Identifiers that refer to a collection type should have plural names.
- Don't include the type in variable names, except to avoid clashes with other variables.

0 comments on commit f720261

Please sign in to comment.