Does the amount of code make a data structure larger? - c#

I have an arraylist of items that only have maybe ten variables in them. But the items have a good bit of code, and I'd like to add more. I'm curious how this will effect the size of my structure. My intuition tells me each one has a stack, but with arguments getting passed around and stuff I've probably not considered I'm unsure. So roughly just how much is code adding to my data structure?

Code does not add to the size of your structure.

The code associated with a class is not usually duplicated per-instance so adding code should not impact the size of your arraylist.

Even though you put code in the same set of curly braces as data, the compiler will separate it out and put it in a different memory section.
That way, you only need one copy of the code - it's not necessary to make a new copy for each item that uses it.
Only in very large projects does the actual size of the compiled code become a problem; usually, it's not much bigger than the source text. On small programs, it's typically a few hundred K or a meg or two at most. It's not worth worrying about on modern machines.

The size of an object instance is (mostly) the sum of its data members. Function members are not stored per-instance, and have no effect on instance size.
Your program has a single stack per thread. When a function is called, stack memory is reserved for each parameter and variable of that function, and freed when it returns.
Your object is stored on the stack if it is instantiated in a function without new. If you use new, only a reference is stored on the stack, and the instance itself is stored on the heap.
:)

Code is not stored on the heap.
Regardless of how many objects you create, you'll only have the code in one place.

The class member functions on which object works are stored differently and it has no effect on size of the object. Where as data members inside the class will be part of the object and object size will change if you change the type of the variable.
ex:
class Test
{
1. member functions
//it does not matter how many functions you have, this section does not contribute
// to object size
2. member variables
//this contributes to the object size, define an int or double etc will change the object size
}

Each object does not have its own stack. Stacks are per thread/process, not per object.

Related

Is there any benefit of working on string directly rather than assigning it to a var?

Is there any benefit of doing this;
private void Method()
{
var data = ConfigurationManager.AppSettings["Data"].Split('-');
}
than doing this;
private void Method()
{
var _data = ConfigurationManager.AppSettings["Data"];
var data = _data.Split('-');
}
Case: I need to read bunch of configuration values like this in the same method, multiple times (let's say every time I instantiate this class).
How will both cases will affect the performance and memory? Or are they pretty much the same things? I see assigning it to a variable will allocate space on memory for no reason.
There will be the same IL code generated in both cases.
And don't forget about The Rules of Code Optimization
The compiler will reduce those to the exact same thing. No, there's no difference in this scenario. If you're ever curious, compile it in release mode, and use ildasm to look at what it did.
However! Performance questions should never be answered by hunch - or even asked on hunch. First, determine if you are actually trying to solve a real problem - otherwise you're probably just yak shaving.
In your first case since ConfigurationManager.AppSettings["Data"] will return a string there is no harm in chaining the Split() method with it than creating a extra variable.
In second case, it would be efficient if ConfigurationManager.AppSettings["Data"] would be used multiple places. In such case, instead of fetching it again and again, you fetch it once, store it to a variable and re-use it.
Both statements are equal. You have a false understanding on when space on your memory is allocated. This actually happens inside the AppSettings-call, not on assignement. Thus when you make any call to a member the result allready exists on memory. Storing this value in a variable does not increase anything - neither memory-allocation nor performance.
However if you´d store the result in a member of your class it´ll be garbage-collected far later than your local data-variable as it doesn´t get out of scope. In this case storing your result to the member will allocate memory as long as the instance exists.
Having said this it is in mostly all cases more important to focus on your code being maintainable, that is if other developers can understand it without asking what all this about.
This means you shouldn´t ask: which horse runs faster but instead which code is easier to understand?

Do i need to free the memory after using a string list with object type

I want to create a collection class that can collect any type of data (string, int, float). So I decided to use a List<object> structure to store any kind of data.
Since using a List structure is safer (managed) than creating an unmanaged array, I want to create a List structure so it can hold any kind of data... but I have some concerns that if I create a List<object> structure and try to hold some strings, there could be memory leaks because of string type..
So do I have to do somethings after using (emptying) the List and deallocate the strings individualy or does .Net already handle that...
Is there a nicer method for creating general collection class?
You won´t need to GarbageCollect any objects on your own as long as you really need to, but according to your post that´s not the case here, actually this is only necessary in a few cases (you may look here what these cases might be).
However .NET frees any memory to which no references exist (indepenedend if you have an int, a string or any custom object), thus if you leave the scope of your array, list or whatever you use the contained elements will be eliminated at some none-deterministic point of time by the GC, but you won´t take care for this.
What you mean by managed and unmanaged is probably the fact, that a List is a bit more dynamic as it can change its size depending on the current number of elements. If this number exceeds a given maximum the list automatically increaes by a given factor. An array is fixed in size however. The term "unmanaged" however relies to C++ e.g., C#-Code is allways managed code (which means there is a garbage-collector e.g.). See Wikipedia on Managed Code

does an object created in a parameter to function get copied to both stacks?

If class x calls y by going y.create(new z) does the z obj get created in x's stack as well as y's? This is assuming we are passing by value, not ref or ptrs
A couple of things:
The stack/heap is on the process (application) level, not at an object level. The entire application shares one stack (at least in the context of your question), no matter how many objects it is using.
Unless the "z" in your example is a value type (like a struct), it won't ever fully reside on the stack. If "z" is a class, then it "lives" on the heap, with only a reference to it on the stack.
You really should read this short explanation from Jon Skeet, especially "A worked example" towards the bottom.
The object z is created in the applications allocated memory. Each function does not have its own memory area when using new to create objects.
I would suggest that you read up on the content on this page, I certainly find it useful from time to time (ie when i get things mixed up)

Limit memory consumption of class

I have a performance counters reporter class that holds in multiple members different lists. Is there a neat way to tell the class the memory limit of its consumption (to be bullet proof case the lists will be pushed with enormous amount of data), or should I go to each member and change it to blocked list? (and this is less dynamic in a way)
What you're asking doesn't make sense. How could a class limit its memory consumption?
Consider: you have a public property that is a list of data. You set the value of that property to be a 2GB set of data but the class is limited to 100MB. How does the class decide what data to throw away? What happens to the data that's thrown away? How does the rest of your program deal with the fact that half its data has disappeared?
None of these questions are sensibly answered, because each program will have a different answer. For that reason, you'd have to implement such logic yourself.
However, more importantly, you should consider this: if I create a List<int> that contains 2GB of data, and assign this list to a property of your "reporter class," the memory consumption of your reporter class doesn't change. This is because your reporter class has a property that is a List<int>, and what that means is that the property stores the memory address of a List<int> that is held somewhere else in the heap. This memory address - a pointer to what we consider the "value" of the property - is fixed according to the architecture of your machine/application and will never change. It's the same size when your pointer is null as it is when the pointer points to a 2GB list. And so in that sense, the memory consumption of your class itself won't be as big as you think.
You can redefine the question to say "when calculating consumption, include all objects pointed to by my properties" but this has its own problems. What happens if you assign the List<int> to a property on two different objects, each with its own memory limit?
Also, if your reporting class has two properties that could hold large data, and I assign large values to each, how do you decide what to throw away? If I have a 100MB limit for the class, and assign 200MB of data to one property and 1GB of data to the other, which data do I truncate? What would happen if I then cleared one of the properties - I now have "spare" memory consumption but data is irretrievably lost.
In short: this is a very complex requirement to request. You'd have to create your own logic to implement this, and it's unlikely you'll find anything "standard" to handle it, because no two implementations would be the same.

Why do we need reference types in .NET

Why do we need reference types in .NET?
I can think of only 1 cases, that it support sharing data between different functions and hence gives storage optimization.
Other than that I could not enumerate any reason, why reference types are needed?
Why do we need reference types in .NET? I can think of only one reason: that it support sharing of data and hence gives storage optimization.
You've answered your own question. Do you need a better reason than that?
Suppose every time you wanted to refer to the book The Hobbit, you had to instead make a copy of the entire text. That is, instead of saying "When I was reading The Hobbit the other day...", you'd have to say "When I was reading In a hole in the ground there lived a hobbit... [all the text] ... Well thank goodness for that, said Bilbo, handing him the tobacco jar. the other day..."
Now suppose every time you used a database in a program, instead of referring to the database, you simply made a full copy of the entire database, every single time you used any of it in any way. How fast do you think such a program would be?
References allow you to write sentences that talk about books by use of their titles instead of their contents. Reference types allow you to write programs that manipulate objects by using small references rather that enormous quantities of data.
class Node {
Node parent;
}
Try implementing that without a reference type. How big would it be? How big would a string be? An array? How much space would you need to reserve on the stack for:
string s = GetSomeString();
How would any data be used in a method that wasn't specific to one call-path? Multi-threaded code, for example.
Three reasons that I can think of off the top of my head.
You don't want to continually copy objects every time you need to pass them to a Method or Collection Type.
When iterating through collections, you may want to modify the original object with new values.
Limited Stack Space.
If you look at value types like int, long, float you can see that the biggest type store 8 bytes or 64 bits.
However, think about a list or an array of long values, in that case, if we have a list of 1000 values then the worst case will take 8000 bytes.
Now, to pass by value 8000 bytes will make our program to run super slow, because the function that took the list as a parameter will now have to copy all these values into a new list and by that we loose time and space.
That's why we have reference types, because if we pass that list then we don't lose time and space to copy that list because we pass the address of the list in the memory.
The reference type in the function will work on the same address as the list you passed, and if you want to copy that list you can do that manually.
By using reference types we save time and space for our program because we don't bother to copy and save the argument we passed.

Categories

Resources