-
Website
http://tirania.org/blog -
Original page
http://tirania.org/blog/archive/2008/Sep-28.html -
Subscribe
All Comments -
Community
-
Top Commenters
-
Max "WorldMaker" Battcher
7 comments · 1 points
-
psantosl
18 comments · 1 points
-
whitemice
8 comments · 1 points
-
barrkel
6 comments · 3 points
-
Ed Ropple
27 comments · 13 points
-
-
Popular Threads
-
C# String Interpolation - Miguel de Icaza
3 days ago · 59 comments
-
Cena Linuxera en el DF, hoy - Miguel de Icaza
8 hours ago · 3 comments
-
New Moonlight Covenant has been posted - Miguel de Icaza
8 hours ago · 2 comments
-
Nine Months Later: Mono 2.6 and MonoDevelop 2.2 - Miguel de Icaza
1 week ago · 43 comments
-
Releasing Moonlight 2, Roadmap to Moonlight 3 and 4 - Miguel de Icaza
5 days ago · 30 comments
-
C# String Interpolation - Miguel de Icaza
I think it makes the code just as easy to read, or easier to read... but certainly not harder to read.
Do you also restrict your development team to variable names with a maximum of 6 characters too? Come on, this isn't 1960.
I also use "this" even when unnecessary, because it makes it a lot easier to see what variables are local and which are at the instance level. For example, "this.some_variable = 5;" or "this.do_something();"
Well, I believe in succinct code. I am not a fan of the baroque style of coding. Just because you can add decorations, does not mean you should.
Would you rather use type inference to call a method, or would you rather type all the types, even when the compiler can figure that out for you?
Would you use explicit casting, just because it would show the real value, even if the compiler does the casting implicitly?
MultiplyMatrix ((double) 1, 2.3);
Would you use:
var x = new List<string> ();
Or would you rather write:
List<string> x = new List<string>();
Implicit is good, leverage it.
For the "var x" example, I always write
List<string> x = new List<string>();
Well, no, that's not quite true--because I have a personal quirk of always using the System.* names for the various base types, so I'd use List<String>, myself.
What you call "baroque", I call "specific". Within reason, I am almost always for anything that enhances specificity. Yes, "private void Blah()" is an extra word. But the symmetry with "public void OtherBlah()" gives it semantic value to me and, I suspect, a lot of programmers.
Verbosity makes it easier to deal with your code later. "Succinct" code is one of the reasons I steer well clear of C and C++. Bringing those bad habits to C# feels kind of painful.
Succinct is what makes Ruby a joy to write web apps, the mandatory idiocy what makes using Java a pain and self inflicted pain what makes C# less than pleasant.
You guys are arguing as if they were paying you by the byte. "private" is the new pay-by-line of code.
I also don't like Ruby; I find it unpleasant, oddly terse, and uncomfortable to use. Different strokes for different folks.
So, you do indeed appear to be confused.
The less context switches you have to make while reading code, the better. Especially when bouncing between languages which may not have the same default access. To me, it is a context switch if I have to stop and recall what the default access is and then continue reading.
var needs to be used in moderation. There are many times where it is extremely inappropriate to use, even though you can.
I am starting to take a shine to Ruby but sometimes I get creepy Perl vibes from some of the things you can abuse in the language. Monkey patching is the devil itself.
What is 1.0 for you double, float, or decimal ? I think you rely on C# compiler to decide.
>>For the "var x" example, I always write
>>List<string> x = new List<string>();
>>Well, no, that's not quite true--because I have a personal quirk of always using the System.* names for the various base types, so I'd use List<String>, myself.
Wow, that's pretty bad. This makes your code very hard to read and you rely heavily on compiler to decide what is String because it's context dependent name.
Consider this
using System;
using System.Collections.Generic;
namespace N
{
class String {}
class Test
{
public static void Main ()
{
var s = new List<string> (); // System.String
var s2 = new List<String> (); // N.String
}
}
}
You decided for option `s2', and it takes me hard time to check your source code to be sure what String is.
You say that like that matters. A programmer won't particularly care if it's a double or a float or a decimal--just that it's not an integer.
>> You decided for option `s2', and it takes me hard time to check your source code to be sure what String is.
Nonsense. "int" is C#, "Integer" is VB, but Int32 is unambiguous across all .NET languages (and more descriptive, too).
Marek knows a thing or two about the C# language, considering that he implemented most of C# 3, and about 40% of our compiler.
Your example about MultiplyMatrix is something that someone coding numerical and scientific codes like me would consider a mistake. You rely on the compiler, and it is not good. It is common practice to _always_ add at least the "dot" when operations are done among double. So, if I agree with you about explicit casting, your syntax should be:
MultiplyMatrix (1.0, 2.3);
It doesn't really cost anything, and it adds information.
Implicit is _wrong_ by definition, and should _not_ be leveraged. All serious programming books say so, at least. :-)
I think it is because var is *about* the variable declaration I am performing, but private is a modifier which works in entirely different space than the declaration itself. Additional reason is that omitting access modifiers does different things in different contexts (think namespace-level classes), so I always have to consider context when reading code.
I also use 'this' for all references.
— Programmer Barbie
More seriously, if you find it confusing to omit "private" from a declaration, then you do not understand the basic philosophy of C#, never mind the specifics of the language. I would not look favourably on a co-worker or underling complaining about this.
Wherever possible, I write my code to be as readable as possible to as large an audience as possible. Specificity and verbosity *are* good; one just has to look at the morass of nigh-unreadable, super-dense C code out there to see why.
Its a matter of preference which is why it is optional. Learn to adapt.
Lets assume that the user does not know it, so he sees that variable, and when he *tries* to access it, he will get a compiler error "The variable you are trying to access is private". Big deal.
Implicit statements are considered "wrong" because they leave the choice to the compiler. It sounds "old school" maybe, but it is the safe way. :-)
If anyone is 'programming defensively' at that level of paranoia (agh - even the compiler writer is against me!) , then their code is going to be incomprehensible.
So i always specify it to make things clear and increase the ease of redabilty. I dont think that would add any over head for compilation/run time process?
If so, let me know.
I think that a programmer must know about the language that he using, and I already had a discussion with a guy that works with me about it... I disagree with the idea that you must write four lines of code because someone could not read that code, because he is not so good as you are...
I already coded without the private, but in this case, I like to write the code on the same format, declare methods or variables on the same way, so I put it... but I think that is just an option, like others here...
We are not living on Saturn. On Earth no one's knowledge/understanding is same/equal to anyone else's. Software parameters are not static. Everything is open to change. Software requirements, design, implementation and developers themselves too. Different developers may try to read the code. And non of them are equal in anyway. So there must be some mid-way to make things/changes/readability be easier. I believe this mid-point is in somewhere private is coded explicitly.
If 4 lines of code is not enough 10/20/30 must be written, just to make readability/change easier.
Do you use {} in an if block even when the block only contains a single statement?
Do you use operator precedence parenthesis even when your expressions do not need parenthesis?
In JavaScript, do you terminate lines with a semicolon;?
Programmers do all of these, because the risk of mistyping and getting it wrong produces hard-to-find bugs. So in the long-run, it is simpler to state the obvious. Adding private onto members and internal onto types, even though they're the default is just keeping the code homogenous.
I just wondered what you meant. Omitting 'private' consistently would be homogeneous too... I suppose. I don't think the word is applicable in either case.
http://blogs.oberon.ch/tamberg/2007-10-30/under...
Regards,
tamberg
I'll stick with Ruby.
Adding 'private' is kind of like putting in an inline comment that states the obvious, since it has zero effect on what gets compiled.
NB: this assumes your code is being maintained by C# programmers (ie - people who know C#)
/*reference semantics*/ class Foo
{
string /*is return type*/ Bar(int a, int b, int c) /*method has 3 parameters*/
{ ... }
}
Some people might not know that.
Arguments like "Implicit statements are considered "wrong" because they leave the choice to the compiler", shows just misunderstanding the problem. Why specify just access modifiers? Do you explicitly state everything where compiler could fall back to C# standard behaviour? Do you declare all your namespace types public, or internal ? Do you avoid type inference? Do you specify best conversion? Do you fully classify types when they are referenced? The list could go on and on.
Also, there is maybe better example than Miguel showed.
Consider this code:
public partial class C
{
partial void Foo ();
}
public partial class C
{
partial void Foo ()
{
}
}
I like consistency and this sums the problem nicely, if you understand C# you know that the method is a private. If you try to explicitly override method accessibility you got a compiler error for C# specific reasons.
public int DoSomething ();
private int DoPublic ();
public void DoNothing ();
public int DoSomething ();
int DoPublic ();
public void DoNothing ();
Why specify just access modifiers?
Well because your HAVE to specify them in 70% of the cases anyways. It just makes no sense to be inconsistent, insymmetrical and less readable just to save a few characters in the rest 30%. Or do you write every program in one single file in one single line? Just because files and linebreaks have no meaning?
Why not just standardize on what everybody does:
Access-Modifier, Special-Modifiers, Return, Methodname
To clarify, I didn't say software-engineering beginner, that's really something else.
Just think of partial methods (already showed in my previous post), explicit interface implementations, top level types.
My point was that stating obvious you decrease readability and it does not matter if your code is 20 lines symmetrical or not.
explicit interface implementations 1)
If you do not declare private methods you cannot directly distinguish between a private method an an explicit interface implementations because in code they might look completely identical although they ARE semantically different. If you use explicit private declaration for private methods and none for explicit interface implementations you can easily spot the difference. Greatly enhances readability.
partial types 2)
Same thing as in 1) is also true for partial types.
top level types 3)
Well a top-level type without modifier is obviously NOT PRIVATE (see original post). So you cannot just assume that always when you do not use the modifier it means "private". Just writing what you means cleans up things (and in fact would result in a compiler error if you do something wrong, although that would obviously be a beginners problem. But nevertheless it doesn't harm anything).
>My point was that stating obvious you decrease readability and it does not matter if your code is 20 lines symmetrical or not.
Sorry, but imho it DECREASES readability GREATLY if you omit private modifiers. I have ABSOLUTELY no idea how it should (obviously???) enhance readibility when not writing them.
I write vocals in written english, too altough you could read everything if you omit them. But just making something shorter does not make something more readable.
Private members can not just become an explicit private implementation, you *always* need to include the type they are implementing explicitly. If they are just private, they do not form part of the interface.
Also another (more common) example (nearly) straight from Mono Code:
bool _viewState;
bool _viewStateMac;
string _errorPage;
bool is_validated;
bool _smartNavigation;
int _transactionMode;
internal int mode;
ValidatorCollection _validators;
bool renderingForm;
string _savedViewState;
ArrayList _requiresPostBack;
ArrayList _requiresPostBackCopy;
ArrayList requiresPostDataChanged;
IPostBackEventHandler requiresRaiseEvent;
IPostBackEventHandler formPostedRequiresRaiseEvent;
NameValueCollection secondPostData;
bool requiresPostBackScript;
bool postBackScriptRendered;
private bool _viewState;
private bool _viewStateMac;
private string _errorPage;
private bool is_validated;
private bool _smartNavigation;
private int _transactionMode;
internal int mode;
private ValidatorCollection _validators;
private bool renderingForm;
private string _savedViewState;
private ArrayList _requiresPostBack;
private ArrayList _requiresPostBackCopy;
private ArrayList requiresPostDataChanged;
private IPostBackEventHandler requiresRaiseEvent;
private IPostBackEventHandler formPostedRequiresRaiseEvent;
private NameValueCollection secondPostData;
private bool requiresPostBackScript;
private bool postBackScriptRendered;
In the second example you imho immediatelly see that one of the fields has a different modifier. In the first you only see that if you actually look line-by-line.
My personal preference is in order of accessibility, private, protected, internal, public.
Actually, I'd prefer to have a C++ like keyword where you could just write
private:
bool _viewState;
bool _viewStateMac;
internal:
int mode;
Maybe one day :)
Some people presupposed that symmetry/explicitness are always good and omitting the modifier reduces symmetry/explicitness. I agree that leaving out the modifier is somewhat less symmetric/explicit (but hey, what about looking at it as "members are private, but you can optionally use a modifier like 'public' or 'protected' to promote it to a higher visibility"?) If you want to be really pro-symmetry/explicitness, then consider the asymmetry of the "static" modifier. Why not require the modifier "instance" in front of every non-static field?
The analogy to prefixing fields with "this" is weak. Looking at a variable reference "x", it isn't instantly identifiable whether the reference is to a local variable or a field -- you need to look for variables definitions that are in scope. That's why "this.x" helps. Field declarations are a completely local thing -- it's instantly clear what the visibility is. If it's lacking a modifier, it's definitely "private". IDE syntax coloring can help you sort through large blocks of definitions with different access modifiers.
You might say "but my IDE highlights member field accesses differently from local variable accesses." That's great. Now you can quickly see that "x" refers to, for example, a field. But let's say you come around later and add a local variable "x" to the method -- then the variable reference silently changes from referring to the field to referring to the local. Note that I'm not necessarily arguing in favor of using the "this" prefix, I'm just saying that the issue is more complex than the default access level issue.
Finally, I noticed people making a mistake that I see quite often in discussions about syntax. People, please get it into your heads that verbosity doesn't always make things easier to read. Miguel said he didn't like "private" because it "makes your code more difficult to read." Now, whether it is easier to read or not is up for debate. But saying something like "why make your code less readable just to save a few characters of typing" is completely missing the point.