﻿<?xml version="1.0" encoding="utf-8"?><rss version="2.0"><channel><title>Ayende @ Rahien</title><link>http://ayende.com</link><description>Ayende @ Rahien</description><copyright>Copyright (C) Ayende Rahien  2004 - 2021 (c) 2026</copyright><ttl>60</ttl><item><title>Neil Mosafi commented on Explain this code: Answers</title><description>Sure, but I don't think the point of this post is to discuss building a lazy wrapper for a list. I will wait and see cos I'm not sure what it's about now!</description><link>http://ayende.com/154882/explain-this-code-answers#comment22</link><guid>http://ayende.com/154882/explain-this-code-answers#comment22</guid><pubDate>Sun, 22 Apr 2012 20:02:53 GMT</pubDate></item><item><title>Ayende Rahien commented on Explain this code: Answers</title><description>Neil,
The inner prop will be null, sure. But I can do the lazy init in a single class, not in all places.</description><link>http://ayende.com/154882/explain-this-code-answers#comment21</link><guid>http://ayende.com/154882/explain-this-code-answers#comment21</guid><pubDate>Sun, 22 Apr 2012 17:28:19 GMT</pubDate></item><item><title>Neil Mosafi commented on Explain this code: Answers</title><description>But the inner list can be null (and will be) so you gain very little apart from a bit of added indirection and possibly a source of some bugs (every property and method will have to lazy initialise the inner list or something similar).
Better to initialise a private readonly field if you want to guarantee non nullness.</description><link>http://ayende.com/154882/explain-this-code-answers#comment20</link><guid>http://ayende.com/154882/explain-this-code-answers#comment20</guid><pubDate>Sun, 22 Apr 2012 16:42:12 GMT</pubDate></item><item><title>Ayende Rahien commented on Explain this code: Answers</title><description>Fabian,
The idea is that you have a "never null" collection.

Don't think just about this scenario, think about how useful it is when you KNOW that a collection can never be null.</description><link>http://ayende.com/154882/explain-this-code-answers#comment19</link><guid>http://ayende.com/154882/explain-this-code-answers#comment19</guid><pubDate>Sat, 21 Apr 2012 09:15:58 GMT</pubDate></item><item><title>Fabian Schmied commented on Explain this code: Answers</title><description>@Ayende: I don't understand the purpose, even after your explanation. Are you saying you did this because you needed to define a static field holding an initialized list, but couldn't use a field initializer? 

If so, why couldn't you use a field initializer?</description><link>http://ayende.com/154882/explain-this-code-answers#comment18</link><guid>http://ayende.com/154882/explain-this-code-answers#comment18</guid><pubDate>Fri, 20 Apr 2012 07:00:15 GMT</pubDate></item><item><title>Clay Ver Valen commented on Explain this code: Answers</title><description>You'll have to ensure inner has been initialized before every public method and get_*.  Not that you can't, but not very elegant either.

Also, make sure to NOT to initialize it to a new instance of "Collection" or you'll get a StackOverflowException.  Instead fully qualify it (e.g. System.Collections.ObjectModel.Collection&lt;T&gt;() ) or use List&lt;T&gt;, etc.
</description><link>http://ayende.com/154882/explain-this-code-answers#comment17</link><guid>http://ayende.com/154882/explain-this-code-answers#comment17</guid><pubDate>Wed, 18 Apr 2012 23:00:13 GMT</pubDate></item><item><title>Gerke Geurts commented on Explain this code: Answers</title><description>Why not be upfront about being immutable and use the following signature instead: public Collection&lt;T&gt; Add(T other)?</description><link>http://ayende.com/154882/explain-this-code-answers#comment16</link><guid>http://ayende.com/154882/explain-this-code-answers#comment16</guid><pubDate>Mon, 16 Apr 2012 06:54:21 GMT</pubDate></item><item><title>Karep commented on Explain this code: Answers</title><description>WTF? What i don't understand. What did you get by writing this class? That that you don't have to 'new' Collection?</description><link>http://ayende.com/154882/explain-this-code-answers#comment15</link><guid>http://ayende.com/154882/explain-this-code-answers#comment15</guid><pubDate>Sat, 14 Apr 2012 21:26:34 GMT</pubDate></item><item><title>SergeyT. commented on Explain this code: Answers</title><description>@Daniel, @Ayende: actually there is even more subtle way to break this code.

Try to add readonly modifier to the "nums" field and run this sample one more time.</description><link>http://ayende.com/154882/explain-this-code-answers#comment14</link><guid>http://ayende.com/154882/explain-this-code-answers#comment14</guid><pubDate>Sat, 14 Apr 2012 20:01:30 GMT</pubDate></item><item><title>Andres commented on Explain this code: Answers</title><description>April fools?</description><link>http://ayende.com/154882/explain-this-code-answers#comment13</link><guid>http://ayende.com/154882/explain-this-code-answers#comment13</guid><pubDate>Sat, 14 Apr 2012 19:06:44 GMT</pubDate></item><item><title>Daniel Grunwald commented on Explain this code: Answers</title><description>@Ayende Try it, I'm fairly sure your example program will break with an automatic property instead of a field.
The actual struct is mutated when the internal list is created on the first Add() call. Your struct behaves like a value type before initialization, and like a reference type after. 
With an automatic property, there's no way to initialize the underlying field; only the properties' return value gets initialized - so in effect every access to the property returns a new collection.</description><link>http://ayende.com/154882/explain-this-code-answers#comment12</link><guid>http://ayende.com/154882/explain-this-code-answers#comment12</guid><pubDate>Sat, 14 Apr 2012 10:28:51 GMT</pubDate></item><item><title>Ayende Rahien commented on Explain this code: Answers</title><description>Daniel,
Actually, no, it would still work.
The internal list is mutated, not the actual struct.</description><link>http://ayende.com/154882/explain-this-code-answers#comment11</link><guid>http://ayende.com/154882/explain-this-code-answers#comment11</guid><pubDate>Sat, 14 Apr 2012 00:16:11 GMT</pubDate></item><item><title>Scooletz commented on Explain this code: Answers</title><description>This code is just wrong. I can imagine a plenty of people reading it and then trying to figure out what's going on. After 15 minutes they would go to the summary of the Collection class, oops! struct and read "Because it allows you to write this sort of code:". Then a facepalm would occur.</description><link>http://ayende.com/154882/explain-this-code-answers#comment10</link><guid>http://ayende.com/154882/explain-this-code-answers#comment10</guid><pubDate>Fri, 13 Apr 2012 19:34:40 GMT</pubDate></item><item><title>Andres commented on Explain this code: Answers</title><description>WTF!</description><link>http://ayende.com/154882/explain-this-code-answers#comment9</link><guid>http://ayende.com/154882/explain-this-code-answers#comment9</guid><pubDate>Fri, 13 Apr 2012 15:00:48 GMT</pubDate></item><item><title>Dmitry commented on Explain this code: Answers</title><description>Why is it a problem to call the default constructor?</description><link>http://ayende.com/154882/explain-this-code-answers#comment8</link><guid>http://ayende.com/154882/explain-this-code-answers#comment8</guid><pubDate>Fri, 13 Apr 2012 11:30:40 GMT</pubDate></item><item><title>Daniel Grunwald commented on Explain this code: Answers</title><description>To elaborate on why such a mutable struct is wrong:

Replace your private static field with a static automatic property, and your example program will print 0. (as it mutates the properties' return value, not the actual underlying field)

This is a massive pitfall! A NotSupportedException (uninitialized Collection is readonly) would be much better.</description><link>http://ayende.com/154882/explain-this-code-answers#comment7</link><guid>http://ayende.com/154882/explain-this-code-answers#comment7</guid><pubDate>Fri, 13 Apr 2012 11:05:48 GMT</pubDate></item><item><title>Daniel Grunwald commented on Explain this code: Answers</title><description>Ouch, so if I copy the struct after it's initialized, the underlying list will be shared, but if I copy it before, then each copy will create its own underlying list?

Mutable structs are very bad, especially if they behave like reference types in some aspects, but not in others. To avoid this issue, the default value should be a read-only empty list - so the struct itself will be immutable, only the underlying list (if any) can be modified. That would make the struct act just like a non-nullable reference type on the outside. You'll get an exception when adding to an uninitialized struct, but it still solves the problem of null references for pure read access (which tend to be much more common than write access).</description><link>http://ayende.com/154882/explain-this-code-answers#comment6</link><guid>http://ayende.com/154882/explain-this-code-answers#comment6</guid><pubDate>Fri, 13 Apr 2012 11:00:49 GMT</pubDate></item><item><title>Thomas Levesque commented on Explain this code: Answers</title><description>@Mads, yes, this is what I had in mind ;)</description><link>http://ayende.com/154882/explain-this-code-answers#comment5</link><guid>http://ayende.com/154882/explain-this-code-answers#comment5</guid><pubDate>Fri, 13 Apr 2012 09:39:22 GMT</pubDate></item><item><title>Mads Topro commented on Explain this code: Answers</title><description>@Thomas: Maybe, Add method is initializing the inner field before use it.</description><link>http://ayende.com/154882/explain-this-code-answers#comment4</link><guid>http://ayende.com/154882/explain-this-code-answers#comment4</guid><pubDate>Fri, 13 Apr 2012 09:36:28 GMT</pubDate></item><item><title>Thomas Levesque commented on Explain this code: Answers</title><description>@Richard, it will initialize all fields to their default value, which is null in the case of IList&lt;T&gt;, so you still have to initialize inner when needed (you can't do it in the constructor, since you can't define a default constructor for a struct)</description><link>http://ayende.com/154882/explain-this-code-answers#comment3</link><guid>http://ayende.com/154882/explain-this-code-answers#comment3</guid><pubDate>Fri, 13 Apr 2012 09:33:37 GMT</pubDate></item><item><title>Richard  commented on Explain this code: Answers</title><description>Structs don't require an initialiser as they always have a constructor that will initialise all its fields. The above code is an abuse of this mechanic.</description><link>http://ayende.com/154882/explain-this-code-answers#comment2</link><guid>http://ayende.com/154882/explain-this-code-answers#comment2</guid><pubDate>Fri, 13 Apr 2012 09:22:12 GMT</pubDate></item><item><title>Buildstarted commented on Explain this code: Answers</title><description>The fact that it's missing an initializer for nums?</description><link>http://ayende.com/154882/explain-this-code-answers#comment1</link><guid>http://ayende.com/154882/explain-this-code-answers#comment1</guid><pubDate>Fri, 13 Apr 2012 09:07:38 GMT</pubDate></item></channel></rss>