Skip to content

Commit da3e535

Browse files
committed
Add documentation for the GCI95 rule
This is for green-code-initiative/creedengo-csharp#92
1 parent 066c97f commit da3e535

File tree

4 files changed

+71
-0
lines changed

4 files changed

+71
-0
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
1111

1212
### Changed
1313

14+
- [#399](https://github.com/green-code-initiative/creedengo-rules-specifications/pull/399) Add C# Rule GCI95 - Use `is` operator instead of `as` operator and null check
1415
- GCI69 Java : calls to hasMoreElements() and nextElement() methods from java.util.Enumeration interface aren't flagged anymore when called in a for loop
1516

1617
- Correction of various typos in rules documentations

RULES.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,7 @@ Some are applicable for different technologies.
7171
| GCI92 | Use string.Length instead of comparison with empty string | Comparing a string to an empty string is unnecessary and can be replaced by a call to `string.Length` which is more performant and more readable. | | 🚫 | 🚫 | 🚫 | 🚫 | 🚫 || 🚫 |
7272
| GCI93 | Return `Task` directly | Consider returning a `Task` directly instead of a single `await` | ||||||||
7373
| GCI94 | Use orElseGet instead of orElse | Parameter of orElse() is evaluated, even when having a non-empty Optional. Supplier method of orElseGet passed as an argument is only executed when an Optional value isn’t present. Therefore, using orElseGet() will save computing time. | [Optimized use of Java Optional Else](https://github.com/green-code-initiative/creedengo-challenge/issues/77) || 🚫 | 🚫 | 🚫 | 🚫 | 🚫 | 🚫 |
74+
| GCI95 | Use `x is string` instead of `x as string != null` | Using the `as` operator followed by a null check is more verbose and can be simplified using the `is` operator with pattern matching. When using the `is` pattern, the type check and cast happen in one concise statement, improving readability and reducing boilerplate. Therefore, using `is` with pattern matching will simplify code and improve maintainability. | [Roslynator Rule](https://josefpihrt.github.io/docs/roslynator/analyzers/RCS1172/) [Microsoft Documentation](https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/operators/type-testing-and-cast) | 🚫 | 🚫 | 🚫 | 🚫 | 🚫 || 🚫 |
7475
| GCI203 | Detect unoptimized file formats | When it is possible, to use svg format image over other image format | | 🚧 | 🚀 | 🚀 || 🚀 | 🚀 | 🚫 |
7576
| GCI404 | Avoid list comprehension in iterations | Use generator comprehension instead of list comprehension in for loop declaration | | 🚫 | 🚫 | 🚫 || 🚫 | 🚫 | 🚫 |
7677
| GCI522 | Sobriety: Brightness Override | To avoid draining the battery, iOS and Android devices adapt the brightness of the screen depending on the environment light. | | 🚫 | 🚫 || 🚫 | 🚫 | 🚫 | 🚫 |

src/main/rules/GCI95/GCI95.json

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
{
2+
"title": "Use 'is' operator instead of 'as' operator and null check",
3+
"type": "CODE_SMELL",
4+
"status": "ready",
5+
"remediation": {
6+
"func": "Constant/Issue",
7+
"constantCost": "1min"
8+
},
9+
"tags": [
10+
"roslynator",
11+
"readability",
12+
"simplification",
13+
"performance"
14+
],
15+
"defaultSeverity": "Minor"
16+
}
Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
Using the `as` operator followed by a null check is more verbose and can be simplified using the `is` operator with pattern matching.
2+
3+
When using the `is` pattern, the type check and cast happen in one concise statement, improving readability and reducing boilerplate.
4+
5+
Therefore, using `is` with pattern matching will simplify code and improve maintainability.
6+
7+
== Non compliant Code Example
8+
9+
[source,csharp]
10+
----
11+
var myObj = obj as MyType;
12+
if (myObj != null)
13+
{
14+
myObj.DoSomething();
15+
}
16+
----
17+
18+
== Compliant Code Example
19+
20+
[source,csharp]
21+
----
22+
if (obj is MyType myObj)
23+
{
24+
myObj.DoSomething();
25+
}
26+
----
27+
28+
[source,csharp]
29+
----
30+
var anotherObj = maybeObj as AnotherType;
31+
if (anotherObj != null)
32+
{
33+
Console.WriteLine(anotherObj.Value);
34+
}
35+
----
36+
37+
== Compliant Code Example
38+
39+
[source,csharp]
40+
----
41+
if (maybeObj is AnotherType anotherObj)
42+
{
43+
Console.WriteLine(anotherObj.Value);
44+
}
45+
----
46+
47+
== Additional Notes
48+
49+
- Pattern matching avoids redundant null checks.
50+
- It ensures the cast object is both non-null and of the expected type.
51+
- It promotes safer and more modern C# practices introduced in C# 7.0 and later.
52+
- Also in [certain cases](https://gist.github.com/StanleySweet/cf6a62ddb1db27c4229804f8a706f323) the assembly is better with is less instructions usually means more performance and less energy consumption.
53+

0 commit comments

Comments
 (0)