Answered by:
Parameters and ref/out and const?

Question
-
Now with a language like c++(if i remember correctly) it was allows good practice to pass any value by reference when you could for performance reasons. The logic behind that is because if you have an object that has a ton of information in it, passing a copy of the whole thing takes longer(and more memory) than just passing an address to that. Does this same thing apply in C#. The reason i ask is because all user objects are references anyways but if you modify a object you passed not by reference(the direct object, not the fields), the object in that scope would be different(with the passed one being left unchanged). Is this something like PHP(as far a theory goes) where variables are passed by reference and only copied when the compiler sees you are trying to modify it?'
Also, does making a parameter const also increase performance like with c++(as i think saying it is const in c++ let the compiler optimize the code a little)?Sunday, January 18, 2009 11:24 PM
Answers
-
In C#, all of the .NET value types are passed by value while the reference types are passed by reference. Strings are passed by reference, but they are immutable. Strings get special treatment for special reasons.
If you have "an object that has a ton of information in it", create a class that defines the fields in it so that it will get passed around by reference. Do not create a struct for the exact reasons that you cited above. It gets passed by value because structs are value types at heart.
The only time I worry about using "ref" and "out" is on the rare occasion when I am passing value types to a method that performs some sort of conversion on it. Not very often.
Bottom line. Use classes to define your complex objects so that they will get passed by reference.
Rudedog =8^D
Mark the best replies as answers. "Fooling computers since 1971."Sunday, January 18, 2009 11:35 PM -
As for constants, declare them as an enum. Structs are rarely used. The most common use is probably to perform InterOp with COM and C++ DLLs.
Mark the best replies as answers. "Fooling computers since 1971."- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:02 AM
Sunday, January 18, 2009 11:38 PM -
void TryThis(Foo f) { Foo g = new Foo(); g.num++; f = g; } void CallTryThis() { Foo f = new Foo(); TryThis(f); int localnum = f.num; //what do you see for "localnum" ? }
You'll see that f.num in the calling method is still the initial value. That's because "f" is passed to "TryThis" by value. Yes, it's a reference that is passed by value.
If you change TryThis so that the parameter is "ref Foo f", then you'll see different behavior - "f.num" will be incremented in the calling method.
Obviously, you can always change a field of the reference object as in your example, since a reference passed by value or by reference is still the same reference.
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:13 AM
Monday, January 19, 2009 4:05 PM -
Here's the thing. There's a bit of an issue describing this simply because the terms "value type" and "reference type" corresponse strongly to "passing by value" and "passing by reference".
Think about it this way. There are only two operations that can really be performed on an existing instance of a class or a struct:
1. Assignment - When the actual variable is assigned. This can happen when a class constructor is called and assigned to a variable, or when an existing instance of a type is assigned to a variable.
2. Changes to fields - When the internal fields of an instance are changed, either through the use of a property or a method (both are constructs designed to change fields).
For terminology, I will use the term "calling method" to represent the method that calls the "called method". The called method is the method that may accept a value type or reference type by value or by reference.
Here is what would happen with all of these:
Reference Type Value Type Passing by
ReferenceAssignment to the called method's variable
will result in changing the reference to heap memory
represented by the calling method's variable.
Changes to fields on the called method's variable
will result in changes to the fields of the calling
method's variable.Assignment to the called method's variable
will result in changing the value of the calling method's
variable.
Changes to fields on the called method's variable
will result in changes to the fields of the calling method's
variable.Passing by
ValueAssignment operations to the called method's variable
will have no effect on the calling method's variable.
Changes to fields on the called method's variable will
affect the calling method's variable. (Unless a previous
assignment operation had first completed).Assignment operations to the called method's variable
will have no effect on the calling method's variable.
Changes to fields on the called method's variable will
not affect the calling method's variable, ever.
Note that an assignment to a reference type doesn't actually assign the value, but it assigns the reference to the value. Assignments within methods where reference types are passed by reference will cause the reference of the calling method's variable to change, whereas for value types, you're changing the value and not just the reference.
David Morton - http://blog.davemorton.net/- Edited by David M Morton Monday, January 19, 2009 4:52 PM fixing the table a bit.
- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:13 AM
Monday, January 19, 2009 4:44 PM -
Rudedog: Your reference is changed because you're using the return type of the method to reset it.
Please see my example.
On a wider level, do you think the compiler allows "ref" on a reference parameter if it made no sense? (see David Morton's post).
Passing a reference type instance using "ref" has different behavior than passing the instance without "ref".
Passing a reference type instance using "ref" allows you to pass back a modified object reference (I'm not talking about changing the internal state of the object here). Passing a reference type instance without the "ref" results in different behavior - the internal state of the object can be changed, but not the actual object reference - i.e., as my example shows, you can't set the reference to point to a new object unless you use "ref".
If someone else can explain this better, please be my guest.
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:13 AM
Monday, January 19, 2009 4:49 PM -
No, it should change both f1 and f2 in this case. You are passing a reference type by value, so changes to the fields on the called method's variable will affect the calling method's variable. That's what you're doing-- changing the fields. (This is assuming that Foo is a class, and not a struct).
To be more precise, "f1" and "f2" are not changed. The value (on the heap) that f1 and f2 refer to is changed. f1 and f2 still point to the same block of memory, it's just that the block has now changed. You're not doing any assignment operation within the method.
And for your second post, yes, passing by reference is using the "ref" keyword, while passing by value is omitting it.
David Morton - http://blog.davemorton.net/- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:11 AM
Monday, January 19, 2009 5:22 PM -
Here's my final code sample. It demonstrates what David said far better than what I botched up trying to say.
static void Main(string[] args) { Foo f1 = new Foo(); Foo f2 = f1; Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); f1 = IncrementFoo(f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); DecrementFoo(f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); ModifyFoo(ref f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); } private static void ModifyFoo(ref Foo f) { f = new Foo(); f.num = 0; }
Mark the best replies as answers. "Fooling computers since 1971."- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:12 AM
Monday, January 19, 2009 6:18 PM
All replies
-
In C#, all of the .NET value types are passed by value while the reference types are passed by reference. Strings are passed by reference, but they are immutable. Strings get special treatment for special reasons.
If you have "an object that has a ton of information in it", create a class that defines the fields in it so that it will get passed around by reference. Do not create a struct for the exact reasons that you cited above. It gets passed by value because structs are value types at heart.
The only time I worry about using "ref" and "out" is on the rare occasion when I am passing value types to a method that performs some sort of conversion on it. Not very often.
Bottom line. Use classes to define your complex objects so that they will get passed by reference.
Rudedog =8^D
Mark the best replies as answers. "Fooling computers since 1971."Sunday, January 18, 2009 11:35 PM -
As for constants, declare them as an enum. Structs are rarely used. The most common use is probably to perform InterOp with COM and C++ DLLs.
Mark the best replies as answers. "Fooling computers since 1971."- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:02 AM
Sunday, January 18, 2009 11:38 PM -
About your answer with ref/out, it seems like you are telling me that the only time to use those is if I am going to be modifying those values (say I need to return more than one value, just use the parameters as extra return values).
But if I pass value types like int, double, char, etc... using ref, would i get a performance increase worth while (say I am build a game engine where every drop of performance would count), would it be worth using in that case?
Now for the const stuff:
Well I am not talking about constant variables but talking about parameters. Take the following c++ method
my_object do_something(int a, string b, my_object c)
{
}
Now lets say I know for a fact that I am only using a, b, and c to retrieve data and that I will not need to modify them and also that the return data will also never need to be modified, i would be able to update my code to let the compiler know that and if would be able to optimize this code(i think c++ does this, can't remember for sure):
const my_object do_something(const int a, const string b, const my_object c)
{
}
Thanks for the help.
Sunday, January 18, 2009 11:55 PM -
I guess my answer to the second part is no since it will not even compile. If you would, i would still like your opinion on the first part.Monday, January 19, 2009 12:02 AM
-
eridius said:
I guess my answer to the second part is no since it will not even compile. If you would, i would still like your opinion on the first part.
It depends upon the value type that you are using. I think a passing a reference means passing 8 bytes. Some value types are smaller, while some are larger.
But, performance is measured by more than just speed. Size of the code is a performance factor, too. I would get it working using proven OOP techniques, and forget most if not all of the programming habits you might have learned using C++. Re-learn new ways to implement them, and some newer ones along the way.
Mark the best replies as answers. "Fooling computers since 1971."Monday, January 19, 2009 12:16 AM -
"Size of the code is a performance factor"?
How do you mean size? do you mean length of variables, files, classes, enumerations, etc... names? I thought when the code was compile and that the byte code the the interrupter read would nullify that. I mean are you tell mean if i keep all my variable, file, class, enumerations, etc... names to the min length(even tho code readability was severely suffer)that the program would execute faster?Monday, January 19, 2009 12:33 AM -
Rudedog2 said:
In C#, all of the .NET value types are passed by value while the reference types are passed by reference.
In the terms 'by value' and 'by reference', the 'value' and 'reference' have nothing to do with value types vs reference types. You can pass value type instances by reference and reference type instances by value.
void PassingValueTypeByReference(ref int i)
{
i = 4; //the argument when calling this method will be changed
}
void PassingReferenceTypeByValue(Foo f)
{
f = new Foo(); //the argument when calling this method is not changed, even though it's changed within the method
}
For reference types, it's true that it's always an object reference that gets passed.
For value types, it's always the entire value instance that's passed since there's no concept of a reference to a value type.
It's unfortunate that the terms "by value" and "by reference" were not named something else - the confusion about this is very widespread.
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)Monday, January 19, 2009 1:54 AM -
well i guess if i now 100% that the parameters is never going to be changed i will just use ref since i am interested in game programming and i want to squeeze every ounce of power i can get.Monday, January 19, 2009 2:01 AM
-
If you're passing reference types, then passing by referernce is slightly faster since copying the reference when passing by value adds a slight hit (but likely not enough to worry about).
For passing value types, it is sometimes faster to pass by value since the instance being marshalled just one way may be enough to outweigh the copying of the value instance. If you are using small value types, such as a built-in integer type, then passing by reference should be faster (no copying should give larger gains than requiring the two-way 'trip').
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)Monday, January 19, 2009 2:11 AM -
David Anton said:Rudedog2 said:
In C#, all of the .NET value types are passed by value while the reference types are passed by reference.
In the terms 'by value' and 'by reference', the 'value' and 'reference' have nothing to do with value types vs reference types. You can pass value type instances by reference and reference type instances by value.
For reference types, it's true that it's always an object reference that gets passed.
For value types, it's always the entire value instance that's passed since there's no concept of a reference to a value type.
It's unfortunate that the terms "by value" and "by reference" were not named something else - the confusion about this is very widespread.
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)
I'm sorry, but I am forced to strongly disagree with your initial assertion. Mainly because you turn right around and contradict yourself in the second statement. I was going to use almost those exact words as my argument to disclaim your assertion.
Also, we know that you can pass a value type by reference. That is the whole point of the post. Which is faster. As I said above, it depends upon the value type involved.
http://msdn.microsoft.com/en-us/library/hhw1f6w5.aspx
That link shows a table of memory allocations for value types. Note that a decimal consumes a lot of memory. The library is acting goofy on me at the moment. Pages and links are not being found. I had wanted to show how many bytes are used by a .NET reference, which I believe is actually 16 bytes.
eridius,
Speed is not the only standard to measure code performance. Compiled size is another way; but in most cases, one that is not as significant as it used to be.
Another is maintenance. If I write code that runs at 98% of the speed of yours, but is 10 times easier to read and understand, which is better. It depends upon your priorities. It would seem that you have one and only one.
Since speed is your only concern, why are you even considering using C# anyway. Managed code takes a major performance hit compared to unmanaged code written in C++, or even assembler. Did you know that you could write assembler directly into C++ files?
Mark the best replies as answers. "Fooling computers since 1971."Monday, January 19, 2009 2:13 PM -
In my second statement I didn't say that reference types are always passed by reference - I said that it's always an object reference that is passed. i.e., the object reference is either passed by value or by reference. Look at my example "PassingReferenceTypeByValue".
This just underscores what I said about the confusion being very widespread - you're not a beginner and even you're not quite separating the value vs reference type concept from passing by value vs passing by reference. As I said these two concepts use the same words "value" and "reference", but they are not the same concept.
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)Monday, January 19, 2009 3:38 PM -
I don't think that I am confusing the words, nor the concepts. Reference types are always passed by reference. Explain this.
class Foo { public int num = 1; }
static void Main(string[] args) { Foo f = new Foo(); Console.WriteLine(f.num); Console.ReadLine(); f = IncrementFoo(f); Console.WriteLine(f.num); Console.ReadLine(); } private static Foo IncrementFoo(Foo f) { f.num++; return f; }
The output is "1", then "2". Is it creating a new object, or modifying the same one? Isn't the "reference" that gets passed around actually a value type anyway?
Mark the best replies as answers. "Fooling computers since 1971."- Edited by Rudedog2 Monday, January 19, 2009 3:59 PM edit
Monday, January 19, 2009 3:57 PM -
void TryThis(Foo f) { Foo g = new Foo(); g.num++; f = g; } void CallTryThis() { Foo f = new Foo(); TryThis(f); int localnum = f.num; //what do you see for "localnum" ? }
You'll see that f.num in the calling method is still the initial value. That's because "f" is passed to "TryThis" by value. Yes, it's a reference that is passed by value.
If you change TryThis so that the parameter is "ref Foo f", then you'll see different behavior - "f.num" will be incremented in the calling method.
Obviously, you can always change a field of the reference object as in your example, since a reference passed by value or by reference is still the same reference.
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:13 AM
Monday, January 19, 2009 4:05 PM -
David Anton said:
void TryThis(Foo f) { Foo g = new Foo(); g.num++; f = g; } void CallTryThis() { Foo f = new Foo(); TryThis(f); int localnum = f.num; //what do you see for "localnum" ? }
You'll see that f.num in the calling method is still the initial value. That's because "f" is passed to "TryThis" by value. Yes, it's a reference that is passed by value.
If you change TryThis so that the parameter is "ref Foo f", then you'll see different behavior - "f.num" will be incremented in the calling method.
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)
The original reference gets changed.
static void Main(string[] args) { Foo f1 = new Foo(); Foo f2 = f1; Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); f1 = IncrementFoo(f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); }
Mark the best replies as answers. "Fooling computers since 1971."Monday, January 19, 2009 4:16 PM -
Here's the thing. There's a bit of an issue describing this simply because the terms "value type" and "reference type" corresponse strongly to "passing by value" and "passing by reference".
Think about it this way. There are only two operations that can really be performed on an existing instance of a class or a struct:
1. Assignment - When the actual variable is assigned. This can happen when a class constructor is called and assigned to a variable, or when an existing instance of a type is assigned to a variable.
2. Changes to fields - When the internal fields of an instance are changed, either through the use of a property or a method (both are constructs designed to change fields).
For terminology, I will use the term "calling method" to represent the method that calls the "called method". The called method is the method that may accept a value type or reference type by value or by reference.
Here is what would happen with all of these:
Reference Type Value Type Passing by
ReferenceAssignment to the called method's variable
will result in changing the reference to heap memory
represented by the calling method's variable.
Changes to fields on the called method's variable
will result in changes to the fields of the calling
method's variable.Assignment to the called method's variable
will result in changing the value of the calling method's
variable.
Changes to fields on the called method's variable
will result in changes to the fields of the calling method's
variable.Passing by
ValueAssignment operations to the called method's variable
will have no effect on the calling method's variable.
Changes to fields on the called method's variable will
affect the calling method's variable. (Unless a previous
assignment operation had first completed).Assignment operations to the called method's variable
will have no effect on the calling method's variable.
Changes to fields on the called method's variable will
not affect the calling method's variable, ever.
Note that an assignment to a reference type doesn't actually assign the value, but it assigns the reference to the value. Assignments within methods where reference types are passed by reference will cause the reference of the calling method's variable to change, whereas for value types, you're changing the value and not just the reference.
David Morton - http://blog.davemorton.net/- Edited by David M Morton Monday, January 19, 2009 4:52 PM fixing the table a bit.
- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:13 AM
Monday, January 19, 2009 4:44 PM -
Rudedog: Your reference is changed because you're using the return type of the method to reset it.
Please see my example.
On a wider level, do you think the compiler allows "ref" on a reference parameter if it made no sense? (see David Morton's post).
Passing a reference type instance using "ref" has different behavior than passing the instance without "ref".
Passing a reference type instance using "ref" allows you to pass back a modified object reference (I'm not talking about changing the internal state of the object here). Passing a reference type instance without the "ref" results in different behavior - the internal state of the object can be changed, but not the actual object reference - i.e., as my example shows, you can't set the reference to point to a new object unless you use "ref".
If someone else can explain this better, please be my guest.
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:13 AM
Monday, January 19, 2009 4:49 PM -
Yes, assigning a reference type that was passed by reference will cause the calling method's variable to point to the target of the assignment performed within the method.
David Morton - http://blog.davemorton.net/Monday, January 19, 2009 4:53 PM -
It must be Monday. This changes both variables, too. I added a new method to my second example.
static void Main(string[] args) { Foo f1 = new Foo(); Foo f2 = f1; Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); f1 = IncrementFoo(f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); DecrementFoo(f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); }
private static void DecrementFoo(Foo f) { f.num--; }
Both f1 and f2 change when DecremntFoo is called. It sounds as if you guys are saying that it should not change when Decrement is called.
Mark the best replies as answers. "Fooling computers since 1971."Monday, January 19, 2009 5:16 PM -
David M Morton said:
Here's the thing. There's a bit of an issue describing this simply because the terms "value type" and "reference type" corresponse strongly to "passing by value" and "passing by reference".
Think about it this way. There are only two operations that can really be performed on an existing instance of a class or a struct:
1. Assignment - When the actual variable is assigned. This can happen when a class constructor is called and assigned to a variable, or when an existing instance of a type is assigned to a variable.
2. Changes to fields - When the internal fields of an instance are changed, either through the use of a property or a method (both are constructs designed to change fields).
For terminology, I will use the term "calling method" to represent the method that calls the "called method". The called method is the method that may accept a value type or reference type by value or by reference.
Here is what would happen with all of these:
Reference Type Value Type Passing by
ReferenceAssignment to the called method's variable
will result in changing the reference to heap memory
represented by the calling method's variable.
Changes to fields on the called method's variable
will result in changes to the fields of the calling
method's variable.Assignment to the called method's variable
will result in changing the value of the calling method's
variable.
Changes to fields on the called method's variable
will result in changes to the fields of the calling method's
variable.Passing by
ValueAssignment operations to the called method's variable
will have no effect on the calling method's variable.
Changes to fields on the called method's variable will
affect the calling method's variable. (Unless a previous
assignment operation had first completed).Assignment operations to the called method's variable
will have no effect on the calling method's variable.
Changes to fields on the called method's variable will
not affect the calling method's variable, ever.
Note that an assignment to a reference type doesn't actually assign the value, but it assigns the reference to the value. Assignments within methods where reference types are passed by reference will cause the reference of the calling method's variable to change, whereas for value types, you're changing the value and not just the reference.
David Morton - http://blog.davemorton.net/
I think Monday morning is now gone.
David, in your table there....I read that as "passing by reference" means using the "ref" keyword. While "passing by value" means not using it, as in my code examples.
Mark the best replies as answers. "Fooling computers since 1971."Monday, January 19, 2009 5:21 PM -
No, it should change both f1 and f2 in this case. You are passing a reference type by value, so changes to the fields on the called method's variable will affect the calling method's variable. That's what you're doing-- changing the fields. (This is assuming that Foo is a class, and not a struct).
To be more precise, "f1" and "f2" are not changed. The value (on the heap) that f1 and f2 refer to is changed. f1 and f2 still point to the same block of memory, it's just that the block has now changed. You're not doing any assignment operation within the method.
And for your second post, yes, passing by reference is using the "ref" keyword, while passing by value is omitting it.
David Morton - http://blog.davemorton.net/- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:11 AM
Monday, January 19, 2009 5:22 PM -
David M Morton said:
No, it should change both f1 and f2 in this case. You are passing a reference type by value, so changes to the fields on the called method's variable will affect the calling method's variable. That's what you're doing-- changing the fields. (This is assuming that Foo is a class, and not a struct).
To be more precise, "f1" and "f2" are not changed. The value (on the heap) that f1 and f2 refer to is changed. f1 and f2 still point to the same block of memory, it's just that the block has now changed. You're not doing any assignment operation within the method.
And for your second post, yes, passing by reference is using the "ref" keyword, while passing by value is omitting it.
David Morton - http://blog.davemorton.net/
Right!
That is the original point I was trying to make to Anton. The reference is not changed. The target of the reference---that referenced object sitting on or in the managed heap---is what gets changed when I omitted the ref keyword.
Anton kept making it sound as if my fields should have different values because the reference---meaning the pointer object sitting on the stack---was getting changed. Changed for one, but not the other, because it was being "re-assigned" is the word I think he used.
Mark the best replies as answers. "Fooling computers since 1971."- Edited by Rudedog2 Monday, January 19, 2009 5:33 PM pointer
Monday, January 19, 2009 5:29 PM -
Speed is not my only concern but if using ref was a simple way to get even a small bit of performance from my application, i would be willing to use that.
Now sure I could go use C++/DirectX from programming my game but from what I have read it is 5X easier and faster(might be even more) to write a game in C#/XNA than it is in C++/DirectX and both can output basically the same thing. Sure the c# version would be slower(generally i hear 5-15%) but it is said that is it much easier to write clean efficent code C# that C++ so i said to myself i would take the 5-15% performance lost to greatly reduce issues like memory management(and from what i read i could even include C++ libraries(dlls) if I needed to). Right now I am not trying to make the Next-Gen AAA MMO RPG game, I am trying to make a solid PC RPG(windows only) indie game that might make a few thousand dollars. If I made that kind of money from this project and wanted to goto the next level I would then go and buy a game engine like Unity3D where I would not have to deal with C++ all that much(if at all) and just use C# for programming the game itself(which Unity3D supports).
Monday, January 19, 2009 5:36 PM -
Rudedog2 said:
Anton kept making it sound as if ...
I'm exhausted. Just look at the examples I posted - they show what I intended for them to show.
Passing reference type instances using "ref" is different than passing without "ref".
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)Monday, January 19, 2009 5:42 PM -
eridius said:
Speed is not my only concern but if using ref was a simple way to get even a small bit of performance from my application, i would be willing to use that.
Now sure I could go use C++/DirectX from programming my game but from what I have read it is 5X easier and faster(might be even more) to write a game in C#/XNA than it is in C++/DirectX and both can output basically the same thing. Sure the c# version would be slower(generally i hear 5-15%) but it is said that is it much easier to write clean efficent code C# that C++ so i said to myself i would take the 5-15% performance lost to greatly reduce issues like memory management(and from what i read i could even include C++ libraries(dlls) if I needed to). Right now I am not trying to make the Next-Gen AAA MMO RPG game, I am trying to make a solid PC RPG(windows only) indie game that might make a few thousand dollars. If I made that kind of money from this project and wanted to goto the next level I would then go and buy a game engine like Unity3D where I would not have to deal with C++ all that much(if at all) and just use C# for programming the game itself(which Unity3D supports).
Very rarely is great code simply written out, megaflop perfect, on the first shot. It tends to evolve. Don't worry about optimization unless you really have to. Here's a suggested work flow.
Make it.
Make it work.
Make it work better.
Mark the best replies as answers. "Fooling computers since 1971."Monday, January 19, 2009 5:45 PM -
David Anton said:Rudedog2 said:
Anton kept making it sound as if ...
I'm exhausted. Just look at the examples I posted - they show what I intended for them to show.
Passing reference type instances using "ref" is different than passing without "ref".
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)
Even tho this is somewhat off topic of my OT let me chime in to is if i understand what you guys are talking about
I am pretty sure I understand that difference between pass a reference object with and without the ref keyword in the parameter list as far as functionality goes. The code has comments to explain everything.1 public void do_something(int a, my_object b) 2 { 3 //lets say that the parameter a was pased with a value of 3 and i do this 4 a = 10; 5 //now the local copy of a inside this method's scope is 10 but outside it is still 3 6 7 //lets says the my object has a public field called name and the passed object had the value of "Joe" and i do this 8 b.name = "John"; 9 //now b.name inside and outside the methods scope is both "John" because b is just a reference to copy of the my_object on the heap but if i do this 10 b = new my_object(); 11 b.name = "Bob"; 12 //now the methods object b references a completely new instance of my_object but the the passed object b still point to the original one. 13 } 1 public void do_something(ref int a, ref my_object b) 2 { 3 //lets say that the parameter a was pased with a value of 3 and i do this 4 a = 10; 5 //now the local copy of a inside this method's scope is 10 and outside it is now 10 6 7 //lets says the my object has a public field called name and the passed object had the value of "Joe" and i do this 8 b.name = "John"; 9 //now b.name inside and outside the methods scope is both "John" because b is just a reference to copy of the my_object on the heap and if i do this 10 b = new my_object(); 11 b.name = "Bob"; 12 //now both the methods object b and the passed b is a reference to a completely new instance of my_object becuase it was declared to be passed my reference 13 }
Is the correct in the way i explained both cases?Monday, January 19, 2009 5:58 PM -
eridius said:David Anton said:Rudedog2 said:
Anton kept making it sound as if ...
I'm exhausted. Just look at the examples I posted - they show what I intended for them to show.
Passing reference type instances using "ref" is different than passing without "ref".
Convert between VB, C#, C++, and Java (http://www.tangiblesoftwaresolutions.com)
Even tho this is somewhat off topic of my OT let me chime in to is if i understand what you guys are talking about
I am pretty sure I understand that difference between pass a reference object with and without the ref keyword in the parameter list as far as functionality goes. The code has comments to explain everything.
1 public void do_something(int a, my_object b) 2 { 3 //lets say that the parameter a was pased with a value of 3 and i do this 4 a = 10; 5 //now the local copy of a inside this method's scope is 10 but outside it is still 3 6 7 //lets says the my object has a public field called name and the passed object had the value of "Joe" and i do this 8 b.name = "John"; 9 //now b.name inside and outside the methods scope is both "John" because b is just a reference to copy of the my_object on the heap but if i do this 10 b = new my_object(); 11 b.name = "Bob"; 12 //now the methods object b references a completely new instance of my_object but the the passed object b still point to the original one. 13 }
1 public void do_something(ref int a, ref my_object b) 2 { 3 //lets say that the parameter a was pased with a value of 3 and i do this 4 a = 10; 5 //now the local copy of a inside this method's scope is 10 and outside it is now 10 6 7 //lets says the my object has a public field called name and the passed object had the value of "Joe" and i do this 8 b.name = "John"; 9 //now b.name inside and outside the methods scope is both "John" because b is just a reference to copy of the my_object on the heap and if i do this 10 b = new my_object(); 11 b.name = "Bob"; 12 //now both the methods object b and the passed b is a reference to a completely new instance of my_object becuase it was declared to be passed my reference 13 }
Is the correct in the way i explained both cases?
Exactly.
David Morton - http://blog.davemorton.net/Monday, January 19, 2009 6:00 PM -
Rudedog2 said:I guess you are right about that work flow, it was just that with the ref keyword you have to use it in the definition and wherever you call it(unlike C++ where it is only in the definition) so it would not be so easy to go from not using it to using it. I will code without using it unless i have to and take it from there.eridius said:
Speed is not my only concern but if using ref was a simple way to get even a small bit of performance from my application, i would be willing to use that.
Now sure I could go use C++/DirectX from programming my game but from what I have read it is 5X easier and faster(might be even more) to write a game in C#/XNA than it is in C++/DirectX and both can output basically the same thing. Sure the c# version would be slower(generally i hear 5-15%) but it is said that is it much easier to write clean efficent code C# that C++ so i said to myself i would take the 5-15% performance lost to greatly reduce issues like memory management(and from what i read i could even include C++ libraries(dlls) if I needed to). Right now I am not trying to make the Next-Gen AAA MMO RPG game, I am trying to make a solid PC RPG(windows only) indie game that might make a few thousand dollars. If I made that kind of money from this project and wanted to goto the next level I would then go and buy a game engine like Unity3D where I would not have to deal with C++ all that much(if at all) and just use C# for programming the game itself(which Unity3D supports).
Very rarely is great code simply written out, megaflop perfect, on the first shot. It tends to evolve. Don't worry about optimization unless you really have to. Here's a suggested work flow.
Make it.
Make it work.
Make it work better.
Mark the best replies as answers. "Fooling computers since 1971."Monday, January 19, 2009 6:02 PM -
Here's my final code sample. It demonstrates what David said far better than what I botched up trying to say.
static void Main(string[] args) { Foo f1 = new Foo(); Foo f2 = f1; Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); f1 = IncrementFoo(f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); DecrementFoo(f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); ModifyFoo(ref f1); Console.WriteLine(f1.num); Console.WriteLine(f2.num); Console.ReadLine(); } private static void ModifyFoo(ref Foo f) { f = new Foo(); f.num = 0; }
Mark the best replies as answers. "Fooling computers since 1971."- Marked as answer by Harry Zhu Wednesday, January 21, 2009 9:12 AM
Monday, January 19, 2009 6:18 PM