Archive for the ‘C#’ Category

LINQ Abuse with the C# 4 dynamic type

Thursday, March 4th, 2010

With C# 4 adding some support for dynamic typing one of the first thing that I wanted to do is use it with LINQ.

I want to do this:

dynamic x;
var h = from y in x where y == 1 select y.something;

But I get error messages on both where and select that says

Query expressions over source type ‘dynamic’ or with a join sequence of ‘dynamic’ are not allowed

Major bummer.

But surely there is something I can do. :)

*the title of this post starts with LINQ abuse… please don’t comment about how stupid and evil this is. I know it. Instead, consider this an exercise in getting to know C# a little better.

The dynamic type is just sugar for the object type and some attributes to which the compiler pays attention.

Lets use object…

object things = new[] { 0,1,2,3,4,5,6,7, };
var whatIwant = from thing in things
                            where thing % 2 == 0
                            select thing;
// or if you like longhand:
var wiw = things.Where(thing => thing%2 == 0).Select(thing => thing);

How does this compile? Well, by making Where and Select resolve to extension methods on object instead of extension methods on IEnumerable<T> (which is what people USUALLY think of when they think LINQ).

public static IEnumerable<dynamic> Select(this object source, Func<dynamic, dynamic> map)
{
    foreach (dynamic item in source as dynamic)
    {
        yield return map(item);
    }
}
public static IEnumerable<dynamic> Where(this object source, Func<dynamic, dynamic> predicate)
{
    foreach (dynamic item in source as dynamic)
    {
        if (predicate(item))
            yield return item;
    }
}

Extension methods on object, then cast to dynamic (extension methods aren’t allowed on dynamic).

It should be short work to fill out whatever LINQ methods are necessary to make whatever LINQ expressions you wish work against dynamic (object) and now you can use LINQ with a source that is typed dynamic.

double.IsNaN is 100 times slower

Friday, February 5th, 2010

Its not just your programming group that can’t get it right. I work in a semi-disfunctional group on contract for a client who, not matter how hard we try, doesn’t seem to listen to basic software engineering principles.

I feel a little better (and a great deal worse after thinking about it) when I see that the largest software company in the world deals with some of the same problems.

I found this gem in the WPFToolkit (it is MSPL) source.

// The standard CLR double.IsNaN() function is approximately 100 times slower than our own wrapper,
// so please make sure to use DoubleUtil.IsNaN() in performance sensitive code.
// PS item that tracks the CLR improvement is DevDiv Schedule : 26916.
// IEEE 754 : If the argument is any value in the range 0×7ff0000000000001L through 0×7fffffffffffffffL
// or in the range 0xfff0000000000001L through 0xffffffffffffffffL, the result will be NaN.        
public static bool IsNaN(double value)
{
    NanUnion t = new NanUnion();
    t.DoubleValue = value;

    ulong exp = t.UintValue & 0xfff0000000000000;
    ulong man = t.UintValue & 0×000fffffffffffff;
    return (exp == 0×7ff0000000000000 || exp == 0xfff0000000000000) && (man != 0);
}

 

My jaw was open pretty far for quite a few seconds as I read this.

My Whole App is a LINQ Expression

Sunday, January 10th, 2010

I just published an application which I consider useful over on codeplex with source hosted on launchpad.

http://wlanchannelinfo.codeplex.com/

https://code.edge.launchpad.net/~evarlast/+junk/WlanChannelInfo

I wrote this because Wifi in my home is very slow. Its so slow I’m tempted to run a network cable to my couch so that even when I’m couch surfing I can have fast access to my server.

In an effort to diagnose my slow Wifi, I tried to see if my neighbors were causing interference by running Wifi on the same or overlapping channel as me. I downloaded netstumbler; it didn’t work. I downloaded some other tool; neither did it.

So I wondered how hard it would be to write my own. It turns out Windows 7 added to the Wlan* api to expose all of the necessary data. After some digging I found the managedwlan project on codeplex. Now I got to play.

Once I figured out the api, I was able to write the entire application with pretty much one LINQ expression:

var client = new WlanClient();
var retval =
from wlanIface in client.Interfaces
from bssentry in wlanIface.GetNetworkBssList()
from network in wlanIface.GetAvailableNetworkList(Wlan.WlanGetAvailableNetworkFlags.IncludeAllAdhocProfiles)
where InterfaceService.GetStringForSSID(network.dot11Ssid) == InterfaceService.GetStringForSSID(bssentry.dot11Ssid)
select new WifiInfo
{
bssentry = GetStringForSSID(bssentry.dot11Ssid),
channel = Wifi.FrequencyChannelMap[bssentry.chCenterFrequency],
frequency = bssentry.chCenterFrequency,
linqQuality = bssentry.linkQuality,
strength = bssentry.rssi,
signalQuality = network.wlanSignalQuality,
wifitype = network.dot11BssType
};

The result of that expression is directly databound to a WPF DataGrid and I can now view the data that I want to.

I really love the platform (C#+.NET) on which I work.

I’m Lazy And I Need My Helpers

Thursday, January 7th, 2010

public static class NumericExtensions
{
public static bool IsZero(this byte number)
{
return 0==number;
}
public static bool IsZero(this short number)
{
return 0==number;
}
public static bool IsZero(this int number)
{
return 0==number;
}
public static bool IsZero(this long number)
{
return 0==number;
}
public static bool IsZero(this float number)
{
return 0==number;
}
public static bool IsZero(this double number)
{
return 0==number;
}
public static bool IsZero(this decimal number)
{
return 0==number;
}
}

I wanted something like this today as I was toggling between NUnit and MSTest. Sure, Assert.That( something, Is(0) ) is readable, but its not portable. Its NUnit only, and for this project, I can’t do that. I also like the english reading of IsZero() vs. Is(0)

I think I’ve stated before that any code on this blog (c) by me and licensed under the MIT/X11 License, but for certain bits of code, I see no point in that. So I’m going to start tagging code with CC0, Unlicense and/or WTFPL.

Learning WPF… For real this time.

Friday, December 11th, 2009

I’ve been diving into WPF, again.

WPF is different now and will be even more different in 4.0. The WPF Toolkit is not an “option” in 3.5, it is a requirement. Just like I wouldn’t want to write .NET Code without certain 3rd party libraries (castle, elevate, etc..), I would not want to write WPF without the toolkit.

WPF in .NET 4.0 includes many things from the WPF Toolkit. The one thing that makes Winforms developers like me feel right at home is DataGrid, but the WPF DataGrid is not DataGridView for WPF. I keep running into surprises.

The latest surprise had to do with a prototype I was building. In Winforms, I often just databind a DataGridView to any IList<T>, and let magic do the rest for me. After all, it is just a prototype.

I tried to do the same thing with WPF DataGrid and I was met with a surprise. Surprise! Don’t do that. As soon as I changed from a IList<T> to an ObservableCollection<T> the binding worked. AutoGenerateColumns=”True” makes it very easy to prototype.

TFS is the new SourceSafe in cost

Sunday, October 11th, 2009

from :
http://blogs.msdn.com/bharry/archive/2009/10/01/tfs-2010-for-sourcesafe-users.aspx

this quote stuck out :

There are 3 main areas that we’ve focused on in 2010 to make TFS attractive to smaller teams:

1. Price – We’re not quite ready to announce the pricing and licensing for 2010 yet but I can tell you that it will be at least as easy and cost effective to get as SourceSafe has been.  Stay tuned for more info on this.

If this is true (and I don’t think it is) it will greatly change the face of .net development organizations over the next few years.

The Ugliest Code I’ve Written in a While

Monday, September 14th, 2009

  1. private EventHandler<MyEventArgs> NameObscured1(IMyForm form)

  2. {

  3.             return new EventHandler<NameObscured2>((sender, eventArgs) =>

  4. {

  5.                 form.TabControl.Enabled = false;

  6.                 IAsyncResult iar = null;

  7.                 Action bg = null;

  8.                 bg = new Action ( () => {

  9.                     NameObscured3((s) => {

  10.                         form.StatusLabel.Owner.Invoke(new Action(() => {

  11.                             form.StatusLabel.Text= s;

  12.                             form.StatusProgressBar.Value +=2;

  13. }));

  14.                         return false;

  15. });

  16.                     NameObscured4(sender, eventArgs);

  17. });

  18.                 Action enableForm = () => { form.TabControl.Enabled = true; form.StatusProgressBar.Value = 0; };

  19.                 AsyncCallback callback = (_) => { form.TabControl.Invoke(enableForm); bg.EndInvoke(iar); };

  20.                 iar  = bg.BeginInvoke(callback, null);

  21. });

  22. }

The question is… How can I make this more readable, and is it worth spending the time to do so?

Nesting lambdas to 4 deep cannot be a good idea, but honestly, factoring each one out to a method might actually make this code LESS readable IMO. In this case, it is just a damned shame that some things can be done cross threads in a Windows Forms application.

I’m guessing this is a sign that I am too tightly coupled and should have some kind of mediator which will then Invoke property updates on the correct thread, but I don’t have that now.

Moral of the story: don’t write nasty nested lambdas like me.

There is more than one way to linq that

Sunday, June 28th, 2009

Eric Gunnerson has a post in which he responds to Justin Etheredge regarding “Is Programming A Generic Skill?

I’ll just say that I agree with them both. There are differences between ability, proficiency and mastery.

A Java programmer can jump into C# and be an able C# programmer immediately. It will take time to become proficient and even more time to develop mastery.

I am proof of this with python. I’ve been an able python programmer for over 10 years now(actually closer to 15), but I never spent enough time in python to call myself proficient and I’m certainly far from a master.

But the thing that Eric said which triggered me to write this is not the generic skill discussion with Justin, it is instead a remark that Eric said about Perl, “… because of TMTOWTDI”.

C# is very much becoming afflicted with There is More Than One Way To Do It. It certainly is both the language and library.

Consider LINQ. LINQ to Objects is a new way to do something which everyone has done differently in the past. When new programmers are exposed to linq, I often hear the question “When do I use linq?” The answer I give is typically “whenever you would use a for loop or foreach loop and if you can’t, figure out how you can".

If we throw away the ‘idiomatic code” to which Eric refers, then a giant bucket of TMTOWTDI is thrown in our face. Do we use properties or fields, events or delegate fields?

For public interfaces, FxCop helps a great deal with guidelines for these things and helping to learn the idioms of the language and framework, but for other things, you are left to yourself. That is why reading others source code is so important. (see the weekly course code)

Expand into libraries and TMTOWTDI explodes. From MSFT alone there is Remoting, Web Services (asmx), WSE, WCF, RIA Services, ASHX, ASP.NET Data Services, all of which have some overlap. Then for data access there is ADO.NET, Linq2Sql, Entity Framework. Even within ADO.NET alone, TMTOWTDI. Do you use a reader? Table Adapter with DataSets? Strongly Typed DataSets?

Open to non MSFT and TMTOWTDI explodes again, to the point where I won’t bother listing anything. There is too much.

I think that library TMTOWTDI will always exist. Even Python has SqlObject, SqlAlchemy and ORM as parts of other frameworks like Zope and Django. But language TMTOWTDI is reasonably well mitigated in Python. This is stated in a single line in PEP20 – The Zen of Python

There should be one—preferably only one –obvious way to do it.

C#, perhaps because it was not a goal and because of its C/Java/Delphi roots, has never had that. There has always been TMTOWTDI in C#.

How useful are your error messages?

Thursday, June 18th, 2009

F.cs(334,8): error CS0539: ‘I.M’ in explicit interface declaration is not a member of interface
F.cs(20,15): error CS0535: ‘C’ does not implement interface member ‘I.M(out string)’

This is a fun example of a poor error message, and I don’t mean because I named my file F, my interface I, my method M and my class C.

Its poor because the underlying code looks like this:

interface I { bool M(out string); }

class C:I { void M(out string); }

Sure, this is obvious now what is going on, I have void, but I should have bool, but my error message doesn’t include that when it shows the type signature.  Now consider what happens when interface I is in an assembly which is given to me. I do not have its source, and there is no documentation. My means of finding the signature of this method are three fold:

  1. lean on visual studio press F12 to go to reference of the interface and VS shows me type signatures
  2. use reflector
  3. monodis mylibrary | grep MethodName

I usually use #1, which is probably why I’ve never seen how horrible this compiler error message is until today. Today, I used #3.

* monodis is from Mono

Browsing NHibernate Source Can Be Beautiful

Thursday, May 21st, 2009

NHibernate is awesome, but when Oren’s blog doesn’t have for what you are looking, and your google-fu is coming up short, it can be challenging to find what you want.

http://nhforge.org – is excellent, but almost never comes up in google searches.

http://nhibernate.sf.net – the sourceforge page redirects to http://nhibernate.org which in turn redirects to the http://hibernate.org nhibernate area.

I often want to browse the source. I just need to quickly see what they have done, and I don’t want to open the nhibernate sln on my system.

http://nhibernate.svn.sourceforge.net/viewvc/nhibernate/

I had to hunt around for more than a minute, to find the above url, but rest assured, it is viewvc pointed to nhibernate svn hosted by sourceforge.

If you can’t tell, I love viewvc.