VB.NET: Combining assignments (operator syntax)
Take a look at this VB.NET code:
list = GeoController.RegionByCountry(country, language)
Region.allByLanguage(key) = list
In C#, I could write this in one line:
Region.allByLanguage[key] =
(list = GeoController.RegionByCountry(country, language))
Is there a way to make this a one-liner in VB.NET, like I can in C#?
EDIT: You all must need some sleep, or else you might be thinking a little harder.
Region.allByLanguage
is a cache.
Here's the context:
Dim list As IEnumerable(Of Region)
Dim key = Region.CacheKey(country, language)
If Region.allByLanguage.ContainsKey(key) Then
list = Region.allByLanguage(key)
Else
list = GeoController.RegionsByCountryAndLanguage(country, la开发者_开发技巧nguage)
Region.allByLanguage(key) = list
End If
Return list
How can you tell me that's not verbose code? Shudders.
Heck, if this was a C# team, I'd just write:
return Region.allByLanguage.ContainsKey(key) ?
Region.allByLanguage[key] :
(Region.allByLanguage[key] = GeoController.RegionsByCountryAndLanguage(country, language));
Do you actually need access to the list
instance also? If not, why not just write it like this?
Region.allByLanguage[key] = GeoController.RegionByCountry(country, language));
Your syntax seems strange for C# also, and I don't think many would write that code that way.
Also, it's no goal in itself to reduce the number of lines of code, if it makes the code less readable as you are trying to do in this case.
If you are assigning to both Region.allByLanguage[key]
and list
, I would prefer two lines of code if I ever were to read your code. Merging both assignments on one line of code seems forced at best, and might have the reader not realize that list
is assigned as well as Region.allByLanguage[key]
.
As an alternative, unless your cache is massive or doing something heavyweight, I would just change the code to something like this:
Dim key = Region.CacheKey(country, language)
If not Region.allByLanguage.ContainsKey(key) Then
Region.allByLanguage(key) = GeoController.RegionsByCountryAndLanguage(country, language)
End If
Return Region.allByLanguage(key)
This way you can avoid the need for single line assignment, and you still reduce the lines of code. You can refactor it back out if performance becomes a problem.
In VB.NET, you cannot assign to a variable and assign that same variable to another variable.
In your code, you're assigning GeoController.RegionByCountry(country, language)
to list
and then assigning list
to Region.allByLanguage[key]
In most cases, this is not a good thing to do as it makes your code more difficult to read.
If you are going to use the list
variable later in the subroutine, it is better to go the VB way; explicitly assign the list
and then assign it to the region. If you're not going to use it later then just assign result of GeoController.RegionByCountry(country, language)
straight away and skip the temporary assignment to the list
variable.
If you insist, however on a 'one-liner', you can use this code I was forced to write when I attempted porting some C# code to VB.NET some time ago:
<Extension()> Public Function AssignAndReturn(Of T)(ByVal source As T, ByRef target As T) As T
target = source
Return target
End Function
You can use it like so:
Region.allByLanguage(key) = GeoController.RegionByCountry(country, language).AssignAndReturn(list)
It evaluates the GeoController.RegionByCountry(country, language)
, assigns it to the list
and then returns the result; which is the list
.
精彩评论