Archive

Posts Tagged ‘Syntax’

Gotcha: use parentheses around ternary op conditional expressions

Just came across the following case in C# that puzzled me momentarily, especially since the strings involved were long enough and the expression was broken on multiple lines:

bool flag = true;
string test1 = flag? "xa" : "xb";
string test2 = "x" + (flag? "a" : "b");
string test3 = "x" + flag? "a" : "b";

The test3 case fails since the compiler tries to evaluate the "x" + flag expression at the left side of the operator ?, complaining that it cannot implicitly convert string to bool.

e.g I accidentally produced the following wrong code while I was trying to refactor some third-party code to make it more readable:

string test3 = “some long string here” +

                     (someFlag)?

                     “some other long string”

                     :

                     “some alternative long string”;

whereas the correct was:

string test3 = “some long string here” +

                     ( (someFlag)?

                     “some other long string”

                     :

                     “some alternative long string” );

The correct one needs the whole conditional expression enclosed in parentheses. In fact, the parentheses around (someFlag) can be skipped. In usually prefer them visually, even when I use just a boolean variable instead of a more complex boolean expression, but in case like this one the x + (someFlag)? a : b can be confusing to the reader of the code, not seeing x + (someFlag) will be treated as the conditional instead of someFlag.

Luckily the C# compiler is deterministic enough and not trying to imply meaning from one’s wrong syntax. Had it been some futuristic AI-based interpreter, well, it might have gotten confused there too.

To avoid this confusion in the first place, probably one could have designed a (bool)?x:y operator instead with parentheses being required around the boolean expression, but people coming from other languages (say C++) might then end up writing bool && (bool)?x:y and expect the condition to be bool && (bool) instead of just (bool), so even that syntax would be problematic.

Speaking of other languages, quoting from Wikipedia article on ternary operator:

C++

Unlike in C, the precedence of the ?: operator in C++ is the same as that of the assignment operator (= or OP=), and it can return an lvalue. This means that expressions like q ? a : b = c and (q ? a : b) = c are both legal and are parsed differently, the former being equivalent to q ? a : (b = c).

So confusion even between languages that share a C-style syntax might not be avoided.

Advertisements

Suggestion: Allow local nested methods inside any code block

It would be nice if one could define methods inside other methods so that they are only accessible in the context of the parent method. In Pascal one could define them at the start of the parent method, before any other commands, but after local variables block, so they could also access the variables of their parent proc.

A trick to implement them could be to make them anononymous methods and assign them to respective local delegates inside the parent method. That way one could also do arbitrary level of such nesting.

Ideally they would also accept an optional inline keyword so that the compiler can inline them (useful for short methods) inside the parent method body (that is the only one allowed to call them anyway [they’re not visible from outside classes or other codeblock in the same class]).

For example, when I refactor code to split a big method to call into other smaller methods, I want them sometimes only to be callable from that original method, and not be accidentally called from elsewhere in my code, including elsewhere in the same class.

Note that in Object Pascal/Delphi such nested methods/procedures/functions could access variables defined at the parent method/procedure/function, since you define them always at the top before the local code.

Implementing the inner methods like you do with anonymous methods allows to grab such local context I believe, so you could allow such inner methods to be defined anywhere inside code blocks to allow access to the variables defined above them in the current code block.

Example syntax suggested:

public void SomeMethod(int i)

{

  if(i>10)

{

    int y = 2;

    void increment(int x) { i = i+x+y; }

    increment(5);

  }

  doSomething( i );

}

 

image

In this screenshot from my enhanced version of Hotspotizer (currently adding speech recognition to that Kinect-based full-body-gestures automation app), I’d like InitSpeechRecognition to only be callable from inside LoadSpeechRecognitionPlugin. I use two methods there to split a bigger method, but I don’t want the 2nd one to be accidentally called from elsewhere in my code.

If you like this suggestion, please vote for it at:
http://visualstudio.uservoice.com/forums/121579-visual-studio/suggestions/9639582-allow-nested-methods-inside-any-code-block

Update:

  • Visual Studio Team commented:

You can do this today:

“`
public void SomeMethod(int i)
{
if (i > 10)
{
int y = 2;
Action<int> increment = x => { i += x + y; };
increment(5);
}
doSomething(i);
}
“`

It’s not the syntax you suggested, but it does do the same thing.

Bertrand Le Roy – .NET – Program Manager

 

  • And this is my reply:

Thanks for the pointer Bertrand, having worked with Object Pascal / Delphi for many years too I like its cleaner syntax on this one

Suggestion: Define scoped variable at C# switch conditional statement

Trying to reuse the conditional value of a switch statment in C# at the fallback “default” code block of it, and looking up if that was supported in C#, I found a related discussion at:
http://stackoverflow.com/questions/29628507/c-sharp-get-switch-value-if-in-default-case

I added a comment there and also elaborated it a bit more at a suggestion (PLEASE VOTE IT UP IF YOU AGREE) to Microsoft’s Visual Studio team for the C# language:
https://visualstudio.uservoice.com/forums/121579-visual-studio/suggestions/9578766-define-variable-in-switch

Wouldn’t it be nicer if you could do the following so that fooResult is only visible in the scope of the switch block and then be able to use it at the "default" (fallback case) subblock of the switch code block?

switch (var fooResult = MyFoo()) //SUGGESTION FOR FUTURE C# SYNTAX
{
  case 0: 
    …
    break; 
  …
  default:
    handleOthersCase(fooResult);
    break; 
}

The alternative of evaluating a 2nd time the value inside the "default" is not optimal and the other alternative of defining a local variable outside of the switch block is also not optimal for garbage collection, code optimization, is prone to code errors by accidentally using that value later on after the switch block instead of using some other variable (mistyping the name) etc. It is better practice to allow one to limit the scope of such variables to only where they’re used

a workaround for protecting the local variable from accidental use later on in a long method is to do

{
  var fooResult = MyFoo();
  switch (fooResult)
  {
    case 0:
      …
      break; 
    …
    default:
      handleOthersCase(fooResult);
      break;

  }
}

that is add an extra {…} outside the var and the switch statements, but it doesn’t look pretty

Suggestion: property and event setting block attached to C# type instance

Instead of having to write in C#

      speechRecognizer = CreateSpeechRecognizer();
      if (speechRecognizer != null)
      {
        speechRecognizer.SomeProperty = someValue;
        speechRecognizer.SomeOtherProperty = someOtherValue;
        speechRecognizer.SpeechRecognized += SpeechRecognized;
        speechRecognizer.SpeechHypothesized += SpeechHypothesized;
        speechRecognizer.SpeechRecognitionRejected += SpeechRecognitionRejected;
      }

I’d prefer to write:

      speechRecognizer = CreateSpeechRecognizer() {
        SomeProperty = someValue,
        SomeOtherProperty = someOtherValue,
        SpeechRecognized += SpeechRecognized,
        SpeechHypothesized += SpeechHypothesized,
        SpeechRecognitionRejected += SpeechRecognitionRejected
      }

that is after any Type I’d like to be able to add {…} block with assignments to its properties, like I can do when I create a new type.

Do note that I also would like this syntax and the existing new Type(…) {…} syntax (which is a subset of this one) to support assignment and removal of event handlers, not just setting of properties, as shown in the example above

If you like this suggestion, vote it up at:

http://visualstudio.uservoice.com/forums/121579-visual-studio/suggestions/9479250-property-and-event-setting-block-attached-to-c-ty

Suggestion: implement ignore keyword or allow missing catch block in C#

This is a suggestion I’ve just sent in via Visual Studio’s “Send a frown” feature (rewritten here a bit differently from memory, since that feedback channel doesn’t allow you to access your previous feedback as the Microsoft Connect or the Uservoice site does) :

Instead of having to write

try
{

}
catch (SomeExceptions)
{
//NOP (ignored)
}

I’d like to be able to write

try
{

}
ignore (SomeExceptions);

and similarly if a finally block is used, allow:

try { … }

ignore(SomeExceptions)

finally { … };

That is, I suggest adding an “ignore” keyword, introduced to C# in order to ignore specific exceptions.

Alternatively, could allow a missing catch block, so that the catch (…) clause would be able to be followed directly by a “;” to end the try/catch statement, or by a “finally” clause and its code (sub)block.

try
{

}
catch (SomeExceptions);

and when finally block is used:

try {…}

catch(SomeExceptions)

finally { … }

I’ve also uploaded this for voting up here:
http://visualstudio.uservoice.com/forums/121579-visual-studio-2015/suggestions/9453432-implement-ignore-keyword-or-allow-missing-catch-bl

Suggestion: Allow new in C# without giving Type

This is a suggestion I’ve just sent in via Visual Studio’s “Send a frown” feature:

Instead of writing statements like:

List<CultureInfo> result = new List<CultureInfo>();

in C# I’d prefer to be able to write

List<CultureInfo> result = new ();

inside the () one would be able to pass contructor parameters and also they should be able to use

SomeClass v = new (someParam) { someProperty = …, otherProperty = … };

syntax, that is be able to initialize properties of the class

What I mean is that I want to omit the type name after the new, since it is deduced from the type I have given to the new var.

Doing

Type v = new (…){…};

is more general from the alternative of doing

  var v = new Type(…){…};

since you would be also able to even do

  someCollectionType.Add(new (…){…});

to add a new member to a typed collection

and also would be able to do

SomeMethod(new (…){…})

where the Type would be deduced from the param of the method (obviously if it is not overloaded with more versions with just 1 param)

Update:

In fact, now that I think of it again, the concept of anonymous types in C# could be merged with the suggested one, making the (…) optional if no constructor parameters are to be used (in anonymous types you only give the {…} part with the properties’ initialization).

The compiler would then resort to making a new anonymous type only if it can’t deduce a type from the usage context.

Of course if the (…) part (constructor parameters) are given, it would never try to make an anonymous type if it can’t find a matching type to instantiate with the respective constructor signature to call.

Have uploaded this for voting up at:

http://visualstudio.uservoice.com/forums/121579-visual-studio-2015/suggestions/9453546-allow-new-in-c-without-giving-type

HowTo: Call C# method from class that has same name as namespace

image

In the C# compiler error case shown above, CaptionsGrid class exists in namespace ClipFlair.CaptionsGrid so in the code we have “using ClipFlair.CaptionsGrid;” at the top of the file where we want to call the “SaveAudio” static method of CaptionsGrid class.

But then we get the error “The type or namespace name ‘…’ does not exist in the namespace ‘…’ (are you missing an assembly reference?)”

The solution is to use a more full identifier, that is use “CaptionsGrid.CaptionsGrid.SaveAudio(…)” or even use the full namespace path “ClipFlair.CaptionsGrid.CaptionsGrid.SaveAudio(…)”. In the last case you wouldn’t need the “using ClipFlair.CaptionsGrid” at all.

It is better to avoid naming the parent namespace part of a class with the same name as the class, but some times one can’t find a better name I guess.

%d bloggers like this: