[Zope-CVS] CVS: PythonNet - README.txt:1.13
Brian Lloyd
brian at zope.com
Sat Jan 17 23:30:06 EST 2004
Update of /cvs-repository/PythonNet
In directory cvs.zope.org:/tmp/cvs-serv26381
Modified Files:
README.txt
Log Message:
Checkin miscellaneous stuff done since Nov.
=== PythonNet/README.txt 1.12 => 1.13 ===
--- PythonNet/README.txt:1.12 Wed Nov 19 22:30:34 2003
+++ PythonNet/README.txt Sat Jan 17 23:29:35 2004
@@ -412,6 +412,81 @@
are returned as unicode.
+ **Value Types And Reference Types**
+
+ The .NET architecture makes a distinction between 'value types' and
+ 'reference types'. Reference types are allocated on the heap, and
+ value types are allocated either on the stack or in-line within an
+ object.
+
+ A process called 'boxing' is used in .NET to allow code to treat a
+ value type as if it were a reference type. Boxing causes a separate
+ copy of the value type object to be created on the heap, which then
+ has reference type semantics.
+
+ Understanding boxing and the distinction between value types and
+ reference types is important when using Python for .NET because
+ the Python language has no value type semantics or syntax - in
+ Python "everything is a reference". This difference can be important
+ in certain situations when you are writing code dealing with
+ managed value types.
+
+ Here is a simple example that demonstrates the issue. If you are an
+ experienced C# programmer, you might write the following code::
+
+ items = CLR.System.Array.CreateInstance(Point, 3)
+ for i in range(3):
+ items[i] = Point(0, 0)
+
+ items[0].X = 1 # won't work!!
+
+
+ While the spelling of 'items[0].X = 1' is the same in C# and Python,
+ there is an important and subtle semantic difference. In C# (and other
+ compiled-to-IL languages), the compiler knows that Point is a value
+ type and can do the Right Thing here, changing the value in place.
+
+ In Python however, "everything's a reference", and there is really no
+ spelling or semantic to allow it to do the right thing dynamically. The
+ specific reason that 'items[0]' itself doesn't change is that when you
+ say 'items[0]', that getitem operation creates a Python object that
+ holds a reference to the object at 'items[0]' via a GCHandle. That causes
+ a ValueType (like Point) to be boxed, so the following setattr ('.X = 1')
+ *changes the state of the boxed value, not the original unboxed value*.
+
+ The rule in Python is essentially: "the result of any attribute or
+ item access is a boxed value", and that can be important in how you
+ approach your code.
+
+ Because there are no value type semantics or syntax in Python, you
+ may need to modify your approach. To revisit the previous example,
+ we can ensure that the changes we want to make to an array item
+ aren't "lost" by resetting an array member after making changes
+ to it::
+
+ items = CLR.System.Array.CreateInstance(Point, 3)
+ for i in range(3):
+ items[i] = Point(0, 0)
+
+ # This _will_ work. We get 'item' as a boxed copy of the Point
+ # object actually stored in the array. After making our changes
+ # we re-set the array item to update the bits in the array.
+
+ item = items[0]
+ item.X = 1
+ items[0] = item
+
+
+ This is not unlike some of the cases you can find in C# where you have
+ to know about boxing behavior to avoid similar kinds of 'lost update'
+ problems (generally because an implicit boxing happened that was not
+ taken into account in the code).
+
+ This is the same thing, just the manifestation is a little different
+ in Python. See the .NET documentation for more details on boxing and
+ the differences between value types and reference types.
+
+
**Security**
Because Python code is inherently unverifiable, Python code runs
More information about the Zope-CVS
mailing list