Do asp.net application variables pass by reference or value? - asp.net

I've discovered recently that when using the Session or Application objects within an ASP.net application, that it passes the values by reference.
This works great most of the time, but now I'm in a place where I truly need a copy of the data, and not a reference to it, since I will discard any changes to it when done processing.
I'm also aware of setting variables in the root of the application, effectively creating global application variables that have a bit better performance and eliminate all the casting craziness of the Session/Application objects.
Does anybody know if the application variables pass by reference or value? I can't seem to dig up any data on the topic and would like to eliminate the code I currently have to "copy" the data from the Application object into a new variable for processing.

This is not an ASP.NET phenomenon per se... it is inherent to the CLI in all of .NET framework. You should take a look at Jon Skeet's classic article on Parameter passing.
Assuming you are dealing with reference types, if you want to clone an object rather than simply copying a reference to the object, you will need to manually clone it. Here's a good article that explains how to deep copy an object and why the MemberwiseClone method creates only a shallow copy of the object.

Actually, what happens by default (assuming you have a reference type rather than a value type) is that it passes a copy of the reference.
So you have a different variable but it's pointing at the same object.

An "Application" variable is just a regular member variable. It works just like any other variable, it's only it's scope that is larger than most.
If the value of the variable is copied or not depends on whether the variable is a value type or not.
If it's a value type, for example int, the value is always copied.
If it's a reference type, for example a List<int> you get a copy of the reference to the object. The object itself is not copied.
So, if what you need to copy is a reference type, you have to explicitly create the copy.

Related

Calling classes from different projects without causing a Circular Reference

I have a solution, with multiple projects. The ones that concern us here are the Website project and the Models project.
The models have a lot of models in Request/Response mode. E.g. If I have a method called GetCustomers, it will be declared like this public GetCustomersResponse GetCustomers(GetCustomersRequest req). This will make sure that if more params are added in the future, I just need to update the model. Hope you get the idea.
All the req/res models are inheriting a baseReq and baseRes respectively. One of the properties included here is called Header, which includes a number of common properties (e.g. SiteId, Currency).
For each Request, I have to call an Initialize method to fill these properties for me (located in the Website project (due to HttpRequest info required). Would it be possible to call this method from the Model project itself (in the constructor), so as to avoid calling the initialize (code repetition) each time? As it is, since the Website referencing the Models, it is not possible to go back due to Circular reference. Is there a way around it, or is it just not possible?
I have tried to look at different articles on the web, but most say that this is just not possible. Others suggested to have a third project, where both projects reference it, but not sure if this works, since I need the HttpContext object.
Any ideas please? Alternatively would I be able to access the HttpContext from within the Models project?

QVector Deep Copy

I'm trying to deep copy my variable:
QVector<PetTeam*> petTeam;
This PetTeam class also has another QVector containing pets and so on. I am looking to deep copy them all so I can use them for states in an minimax AI but so far I have been unable to deep copy it correctly.
If anyone could provide any insight on the correct way to deep copy in this situation it would be much appreciated!
If you want to copy all PetTeam objects automatically, you need to declare your vector as QVector<PetTeam> petTeam. It requires PetTeam to have a constructor without parameters and a copy constructor. They are generated automatically but you should reimplement them if PetTeam contains any information that can't be copied trivially (e.g. file handlers, pointers to manually allocated memory, etc.)
Another option is to copy your objects manually, i.e. iterate over the list and create a new object for each old object using new PetTeam(...) and then put them in the new list.

ASP.NET. Is it better to pass an entire entity to a method or pass each property of this entity as parameters?

We're developing a business ASP.NET application. Is it better to pass an entire entity to a method or pass each property of this entity as parameters? What is the best practice?
Case 1. Pass Customer entity to a manager - InsertCustomer(Customer cust)
Case 2. Pass each property as a parameter - InsertCustomer(string name, string address...etc)
P.S. We're using Entity Framework as our data access layer
Pass the entire entity, not only for reasons given in the other answers, but generally methods with long parameter chains are bad. They are prone to error, and tough to work with from a development standpoint (just look at Interop with Office)
In general, if I see I am getting too many parameters (usually more than three), either I have a method trying to do too much, or I explore ways of encapsulating this data in a struct.
You should pass the entire entity as when you update the entity, e.g. add or remove members you do not have to update all your method calls in all your layers. You only need to change your datalayer and the layer where you are consuming the entity. asp.net is Object Oriented and therefore you should orientate your code around your objects
The whole concept of object orientation requires objects to be passed around. If all is happening internally I would go with this.
If this is being posted to a webservice / across a network etc you would need to serialize, and hence may find it better to pass each individual parameter, especially if the receiving framework is different.
Don't forget your Strings etc are all objects too.
I agree with another poster, passing a whole entity "encapsulates" everything so that it can be updated/modified so you have less to worry about.

Asp.net error object not set to a reference

Because I rush in development (a lot of whip cracking here) and declare my objects at the top of the function and instantiate inside my try-catch block, I get a lot of the good old "object not set to an instance of an object" errors while doing TDD, and later if I do miss a branch that object was used in (doing VB now, would prefer C#) or just in every day coding, object not set to an instance of an object is a bit vague. Sure the stack trace sends me to the line the error occured at, but it would be nice if I could modify my logging to either name the object or its type because sometimes I have multiple objects on the same line. It's not the end of the world, but in the end it would save me a few minutes each day. Any ideas on how I can pass the info on which object wasn't set? Thanks
It is non trivial to "modify your logging" to output variable name or type - I am sure that if the framework could easily get this information from the executing IL, MS would have included it the null reference exception.
Prevention is always better than cure. Here are a couple of tips I would do
Fix your compiler warnings
C# would generate a compile error if it detects that there are code paths that could use an unassigned local variable. [For some odd reason] VB.Net will still compile but the compiler will generate a warning - take heed of these and go and fix the code and you should never run into the problem of unassigned variables again!
Adopt a different coding pattern for variable declaration
I appreciate that method variable scope in ye olde VB was that the variable was visible throughout the entire method regardless of where it was defined. As a result, it was a reasonable practice to put all your var declarations at the top of the method. VB.Net of course is different - you can only use variables after they are declared and so it is OK (and I would say preferable*) to put the declaration (and assignment) closer to where the variable is actually used. This should help you see "by eye" if your program logic means it is possible to use an unassigned variable.
Some people think this is a think that it is always good practice to put variable declarations in a block at the top of the method. I will not argue against them but I would say that that approach works best with small methods that do not use lots of variables.

Is there a tool to capture an objects state to disk?

What I would like to do is capture an object that's in memory to disk for testing purposes. Since it takes many steps to get to this state, I would like to capture it once and skip the steps.
I realize that I could mock these objects up manually but I'd rather "record" and "replay" real objects because I think this would be faster.
Edit: The question is regarding this entire process, not just the serialization of the object (also file operations) and my hope that a tool exists to do this process on standard objects.
I am interested in Actionscript specifically for this is application but...
Are there examples of this in other
programming languages?
What is this process commonly called?
How would this be done in
Actionscript?
Edit:
Are there tools that make serialization and file operations automatic (i.e. no special interfaces)?
Would anybody else find the proposed tool useful (if it doesn't exist)?
Use case of what I am thinking of:
ObjectSaver.save(objZombie,"zombie"); //save the object
var zombieClone:Zombie = ObjectSaver.get("zombie"); // get the object
and the disk location being configurable somewhere.
Converting objects to bytes (so that they can be saved to disk or transmitted over network etc.) is called serialization.
But in your case, I don't think that serialization is that useful for testing purposes. When the test creates all its test data every time that the test is run, then you can always trust that the test data is what you expect it to be, and that there are no side-effect leaking from previous test runs.
I asked the same question for Flex a few days ago. ActionScript specifically doesn't have much support for serialization, though the JSON libraries mentioned in one of the responses looked promising.
Serialize Flex Objects to Save Restore Application State
I think you are talking about "object serialization".
It's called Serialization
Perl uses the Storable module to do this, I'm not sure about Actionscript.
This used to be called "checkpointing" (although that usually means saving the state of the entire system). Have you considered serializing your object to some intermediate format, and then creating a constructor that can accept an object in that format and re-create the object based on that? That might be a more straightforward way to go.
What is this process commonly called?
Serializing / deserializing
Marshalling / unmarshalling
Deflating / inflating
Check out the flash.utils.IExternalizable interface. It can be used to serialize ActionScript objects into a ByteArray. The resulting data could easily be written to disk or used to clone objects.
Note that this is not "automatic". You have to manually implement the interface and write the readExternal() and writeExternal() functions for each class you want to serialize. You'll be hard pressed to find a way to serialize custom classes "automatically" because private members are only accessible within the class itself. You'll need to make everything that you need serialized public if you want to create an external serialization method.
The closest I've come to this is using the appcorelib ClassUtil to create XML objects from existing objects (saving the xml manually) and create objects from this xml. For objects with arrays of custom types it takes configuring ArrayElementType Metadata tags and compiler options correctly as described in the docs.
ClassUtil.createXMLfromObject(obj);
CreateClassFromXMLObject(obj,targetClass);
If you're using AIR, you can store Objects in the included local database.
Here's a simple example using local SQLite database on the Adobe site, and more info on how data is stored in the database.

Resources