Talk:Flyweight pattern

message: Note:  I just fixed the bug described below.  —Preceding unsigned comment added by 74.68.108.87 (talk) 21:59, 8 April 2010 (UTC)
thread_title: Bug in Java example?

message: Flyweight is a software design pattern.
The sentence above is how the articles title "builder pattern", "adapter pattern", etc. should begin.  Someone who is ignorant of computer software looking at those articles should be told right at the beginning that that is what the article is about.   -- Mike Hardy
Chnged the method printAtPosition() to a static one as the point of a flyweight object was to save memory.   -- Jari Mustonen
each GraphicChar takes 10 bytes of heap space (8 overhead + 2 char + 4 string pointer for font)
8 + 2 + 4 = 14, not 10
--195.6.224.137 15:17, 18 October 2006 (UTC)
thread_title: comment

message: The article should outline the importance of being thread-safe when the Flyweight is static.
The Java example should also be thread-safe, some one who doesnt know this pattern may fall in this trap.  —Preceding unsigned comment added by 81.252.131.1 (talk) 09:11, 15 April 2009 (UTC)
thread_title:  Thread safety issue 

message: The Java example adds WeakReferences into the flyweightData map but at no point removes them.
This could in time lead to a very large map, whose values would mostly end up being null-valued WeakReferences.
Actually it doesn't because the map used is a WeakHashMap and the keys are the same as the referenced value. This approach works nicely when object creation cost is low and the object itself can be used as the key.
When object creation is high and needs to be avoided as well as keeping memory usage down some sort of other key needs to be used.
If the object's hashCode can be replicated with the same parameters given in the constructor then the hashCode is a good choice.
But now you definitely have the problem of the map potentially growing large with null-valued WeakReferences.
The solution is to attach a ReferenceQueue that removes the entry from the map.
org.apache.commons.collections.map.ReferenceMap provides a basic solution for this,
but there exists a superior solution, also open sourced, here
http://sesat.no/projects/sesat-commons/commons-reference-map/
> This implementation improves over org.apache.commons.collections.map.ReferenceMap 
> in that the synchronisation and concurrency is determined through delegation to the 
> map supplied in the constructor as described above. 
Michaelsembwever (talk) 21:48, 20 March 2008 (UTC)
thread_title:  Memory issue in the Java example 

message: I removed this section from the article:
=== VB.NET ===
' The "PersonFlyweight" is a "Person" stripped of all fields (to save memory) that 
' are not used in the immediate task at hand.  This is appropriate when loading millions of 
' objects into memory at once.
Class PersonFlyweight
   Public Sub New(p As Person)
      Me.FirstName = p.FirstName
      Me.LastName = p.LastName
   End Sub
   Public FirstName As String
   Public LastName As String
End Class
' "Person" entity with many fields.
Class Person
   Public FirstName As String
   Public LastName
   Public Address As String
   Public PreviousAddress As String
   Public PhoneNumberHome As String
   Public PhoneNumberWork As String
   Public PhoneNumberCell As String
   Public PhoneNumberFax As String
   Public Height As Double
   Public Weight As Double
End Class
To me it doesn't look like a Flyweight. It may be a pattern to save memory, but to me it doesn't look anything like the Flyweight pattern.
Am I wrong?
--Teglsbo (talk) 12:50, 21 April 2008 (UTC)
thread_title:  VB.Net example: Is this a flyweight? 

message: ' The "PersonFlyweight" is a "Person" stripped of all fields (to save memory) that 
' are not used in the immediate task at hand.  This is appropriate when loading millions of 
' objects into memory at once.
Class PersonFlyweight
   Public Sub New(p As Person)
      Me.FirstName = p.FirstName
      Me.LastName = p.LastName
   End Sub
   Public FirstName As String
   Public LastName As String
End Class
' "Person" entity with many fields.
Class Person
   Public FirstName As String
   Public LastName
   Public Address As String
   Public PreviousAddress As String
   Public PhoneNumberHome As String
   Public PhoneNumberWork As String
   Public PhoneNumberCell As String
   Public PhoneNumberFax As String
   Public Height As Double
   Public Weight As Double
End Class
To me it doesn't look like a Flyweight. It may be a pattern to save memory, but to me it doesn't look anything like the Flyweight pattern.
Am I wrong?
--Teglsbo (talk) 12:50, 21 April 2008 (UTC)
thread_title:  VB.NET 

message: The illustration seems to illustrate an object pool, not a flyweight setup. While object pools can be handy when dealing with flyeights, it isn't directly relevant to the design pattern. The illustration outright fails at communicating the concept correctly.--Henke37 (talk) 19:07, 8 July 2012 (UTC)
replies: text: While we're on the subject, i would say that every code example on the page indicates to me that their authors did not understand this pattern. They do not illustrate the pattern as described at all. I am inclined to remove them. --Rob* (talk) 08:17, 14 November 2015 (UTC)
thread_title:  Illustration 

message: The construct '__slots__' in Python does not, as the article states, 'automatically enable the Flyweight pattern for that class.' It simply removes the backing dictionary ('__dict__') in favor of a tuple. As the definition of Flyweight states at the beginning of the article, the requirement for this pattern is 'sharing as much data as possible with other similar objects.' Two slotted Python classes initialized to the same value will be different objects. 'arr=[foo(1) for i in range(1000)]' will contain 1000 different objects, not 1000 references to the same object. NO PYTHON OBJECT IS IMMUTABLE. For this reason, I don't believe this Python example is valid and should be removed.  — Preceding unsigned comment added by 207.10.138.156 (talk) 22:38, 24 November 2013 (UTC)
thread_title:  Python __slots__ example 

message: Can somebody please fix this? The complexity, BMW advertising and lack of clarity (say Vs C# original Coffee example) is astounding. The original Coffee example, pre BMW, whilst a lot shorter and simpler is also flawed, using ConcurrentHashMap but then also using synchronize everywhere. It's like nobody has read Concurrency In Practice/even bothered learning that those 2 APIs are intended to be (mostly) mutually exclusive replacements for each other.  — Preceding unsigned comment added by 2A02:C7D:31E1:4600:41DD:FF41:6751:5860 (talk) 09:46, 14 October 2018 (UTC)
thread_title:  Java example is a joke 

message: What's up with class ReducedMemoryFootprint in the C# example? It appears it does the same thing as MinimumMemoryFootprint only worse, and is harder to read and understand. The class names are confusing, as you'd expect MinimumMemoryFootprint to use less memory than ReducedMemoryFootprint, but it doesn't. There's no text to explain the code; not even comments. The private method AddFlavourToCache(object state) takes an object instead of a CoffeeFlavour for no discernible reason. I think the example should be removed, leaving just the "Simple Implementation" example. Am I missing something?
-
I agree strongly. Adding cache locks for concurrency seems particularly confusing for anyone who just wants to see what the pattern looks like in action. If nobody objects, I'll remove the large example soon. Telemachus12389 (talk) 11:30, 9 June 2021 (UTC)
thread_title:  C# example is confusing 

message: I've made some minor edits to remove language in this section that sounds like it came from a tutorial (lots of 'you should do this in your application...'). But in general I'm unsure most of the detail here is really relevant - can someone with deep knowledge on the topic highlight any sections that it would be fine to remove in the sake of concision and clarity?
This also seems to be common on other design pattern pages, but I'm not sure what's gained by having examples from nine different languages - especially when some of them, like Java and C#, are so similar. The examples take up over three-quarters of the page, making it feel more like a reference manual than an encyclopedia page. Can any examples by removed? Telemachus12389 (talk) 11:28, 9 June 2021 (UTC)
thread_title:  Implementation details section is unsourced, complex, and basically unreadable 

message: I've gone ahead and cut out big swathes of the implementation details section and several of the code examples. The page still doesn't have enough citations for the implementation details section, but hopefully it now reads more like an encyclopedia page and less like a design manual. Deciding which language examples to cut out was ultimately arbitrary, of course, but I decided to remove some of the slightly less popular languages (Scala, Crystal) and the Java example, since the language is similar to C#. 
I'm aware these are big changes, so feel free to revert the edits. But if you do, I would appreciate hearing why you think the material was worth bringing back, as it would help contextualise its place in the article and improve the piece overall.
Telemachus12389 (talk) 11:31, 12 June 2021 (UTC)
thread_title:  Large changes, feel free to revert if felt necessary 

message: I think the way how WeakReference object is used in CoffeeFlavour::intern() function does not make sense. The WeakReference object should be stored in the cache. In the example classical reference (not weak reference) is stored in the cache which means it will be preserved in the cache all the time. The function should also deal with situation when weak reference has already been forgotten and should refresh it in that case. For that reason, I think the function should return the object itself rather than WeakReference.
Here is an example fix of the function.
public static function intern(string $name) : CoffeeFlavour {
    if (isset(self::$CACHE[$name])) {
        $cachedFlavour = self::$CACHE[$name]->get();
        if ($cachedFlavour !== null) {
            return $cachedFlavour;
        }
    }
    $flavour = new self($name);
    self::$CACHE[$name] = \WeakReference::create($flavour);
    return $flavour;
}
Secondly, we should also remove ->get() from Order::of() function, because ::intern() function already returns the object itself now.
public static function of(string $flavourName, int $tableNumber) : callable {
    $flavour = CoffeeFlavour::intern($flavourName);
    return fn() => print("Serving $flavour to table $tableNumber ".PHP_EOL);
}
See also this example of WeakReference usage (example no. 2) which is similar to my fix.
Mk90461 (talk) 14:02, 20 July 2021 (UTC)
thread_title:  PHP example - cache implementation using WeakReference 

message: The Python example seems to be based on an incorrect understanding of the pattern. It's simply inserting and retrieving from a shared dictionary, but a shared dictionary by itself is not a flyweight pattern. Besides it seems to be largely original research and contains a large off-topic discussion of immutability in Python's data model. I'm WP:BOLDLY removing the section as the other examples illustrate the concept better. 2A02:A44A:5C96:1:D66A:D92F:5729:7268 (talk) 12:14, 30 April 2023 (UTC)
thread_title:  Python example - wrong and off topic?