DCSIMG
November 2008 - Posts - IronShay

November 2008 - Posts

Dynamic Languages and The .Net Framework - Promo #4 - With Our Powers Combined

image This is the 4th part of my series about dynamic languages in the .Net framework. You can read the rest of the series here:

This time, I'm going to show you a sneak peek of the great things you can do with .Net and dynamic languages powers combined.

Ruby allows you to extend every class you want - very similar to .Net's extension methods. IronRuby allows you the same thing, with the added possibility to extend .Net objects.

With our powers combined we are... Dynamic Languages and The .Net Framework! Take for example the next code block, where I extend the DataRow object and adds a print_me method that prints the row's columns and values:

class System::Data::DataRow
    def print_me
        self.table.columns.each do |col|
            print "#{col.ColumnName}: #{self.get_Item(col.ColumnName)}\t"
        end
    end
end

The print_me method goes over the table columns and prints out the column name and current value.

Now, you can loop over your dataset rows and print them with ease:

my_dataset.Tables.get_Item(0).rows.each do |row|
    row.print_me
end

Now you're probably thinking "I can do that with extension methods and I don't have to leave my beloved static language".  Well, you're right! But now I want to introduce you with something you can't do in pure .Net!

Ruby has this great possibility - the method_missing method. This method is called whenever the code generates a call to a method that doesn't exist. This technique is used quite widely through Ruby frameworks. For example, you can call a method like add_Shay_to_list and the method_missing method will interpret the call and add "Shay" to the list... 
Now we're gonna take it and give .Net DataSets a new and powerful feature!

In the next code block I will create the possibility to access data rows directly, using them like if they were properties.
For instance, if I have a record with the value "John Doe" in the Name column, I'll be able to access it by calling my_dataset.John_Doe. As simple as that! along with the print_me method that we have declared earlier, we can call my_dataset.John_Doe.print_me in order to print John Doe's row details. Hysterical! :)

All the code I need to write in order to achieve that is:

class System::Data::DataSet
    def method_missing(name, *args)    
        userName = name.to_s.gsub("_"," ")
        
        result = self.tables.get_Item(0).select("Name = '#{userName}'")
        
        if (result != nil) 
            return result[0]
        end
    end     
end

(I assume here that I have a table and it has a column named Name).

That's it! I've given this powerful feature to every dataset I use in my code!

Now for the whole project code - it includes a simple dataset generation and an example of using the new and shining DataSet feature:

class System::Data::DataSet
    def method_missing(name, *args)    
        # replace '_' with spaces
        userName = name.to_s.gsub("_"," ")
        
        # select the value from the table
        result = self.tables.get_Item(0).select("Name = '#{userName}'")
        
        if (result != nil) 
            return result[0]
        end
    end     
end

class System::Data::DataRow
    def print_me
        self.table.columns.each do |col|
            print "#{col.ColumnName}: #{self.get_Item(col.ColumnName)}\t"
        end
    end
end

ds = System::Data::DataSet.new
# create a table
users_table = ds.tables.add "Users"

# create columns
users_table.columns.add "Name"
users_table.columns.add "Email"
users_table.columns.add "Phone"

# fill data
users_table.rows.add("Iron Ruby","iron@ruby","03-999123")
users_table.rows.add("Iron Python","iron@python","03-812121")
users_table.rows.add("John Doe","john@doe.com","001-22323-231114")

# use the new feature in order to access records directly
ds.Iron_Ruby.print_me
ds.John_Doe.print_me

Haven't had enough? come to my session about dynamic languages and the .Net framework at the Developer Academy III event! :)

All the best,
Shay.

kick it on DotNetKicks.com

IronPython and DLR New Releases

IronPython and DLR New Releases IronPython has just gone RC2. This should be the last release before the final version that is expected to arrive very soon.
Get IronPython RC2 from: http://www.codeplex.com/IronPython/Release/ProjectReleases.aspx?ReleaseId=19841

The DLR project has a new home on CodePlex and it is no longer needed to get IronPython or IronRuby in order to get the DLR code.
The new DLR home is at: http://www.codeplex.com/dlr
There is a new version - 0.9 beta that was released 3 days ago and is available for download here.

Enjoy the new dynamic playground!
Shay.

Posted by shayf | with no comments

IronRuby Tip: Access .Net Indexers

The Problem

IronRuby Tip: Access .Net Indexers  Currently, if you have a .Net class you want to access via IronRuby, and you have an indexer there (like myObject[2]), you won't be able to use the indexer with brackets [] from IronRuby. You'll get an exception.

The Solution

Use get_Item(index) instead (pay attention to casing).

Example

my_dataset.Tables[0] # <-- This won't work
my_dataset.Tables.get_Item(0) # <-- This will work great!
All the best,
Shay.
Posted by shayf | with no comments

The nice thing about blogging...

The nice thing about blogging is that when you blog about new stuff, you get to hit the first page of related google searches!

I've just discovered that one of my posts appears second (!!!) on the search results of "dynamic languages .net framework".

image

Sweet!

Shay.

Posted by shayf | 2 comment(s)
תגים:

Dynamic Languages and The .Net Framework - Promo #3

This is the 3rd promo post to my session at Developer Academy III. Read the rest of the series:

This time I'd like to introduce you with 2 language specific possibilities that will demonstrate how intuitive these languages are...

Creating Enumerable Classes

Let's think of C# enumerators. In order to create objects that support enumerations, you'll have to inherit from IEnumerable and implement an IEnumerator object as well. You can also use yield for that (a post I've written about that can be found here) which simplifies the things a bit.
Now, close your eyes and try to think of a more intuitive way for doing so......................
Good, so what have you come up with? you can add a comment with your ideas.

Ruby has it figured out - just override the Each method and you're good to go... As simple as that!

class MyEnumerableClass
    def initialize(max)
        @max = max
    end
    
    def each
        (1..@max).each { |i| yield i }
    end
end

my_class = MyEnumerableClass.new(8)
my_class.each { |num| puts num }

This code will end up printing the numbers 1 to 8 on the screen.

Breaking From a Loop

The Python guys have realized that one of the major things people do with loops is to search for things in a collection. So we've ended up with a possibility to know that our loop has finished because it went through all of the items in the collection, without breaking away.

for i in nums:
    if i == 10:
        break    
else:
    print "10 wasn't found"
In this example, if nums contains 10, the code will continue. If nums doesn't contain 10, "10 wasn't found" will be printed to the screen.

Haven't had enough? come to my session at Developer Academy III! :)

All the best,
Shay.

Posted by shayf | with no comments

.Net Tip: Console.Out

Shabat Shalom everyone!

The Problem
Sometimes you want your output to get written to the console and all you have is a method that receives a stream to output to. For example, DataSet.WriteXml gets different types of streams or a file path to write to...

The Solution
If you want to output the result to the screen, use Console.Out as your stream:

DataSet d = GetDataSetFromSomewhere();
d.WriteXml(Console.Out);

That's it!

All the best,
Shay.

Posted by shayf | with no comments

Visual Studio Tip: Line Break in String Properties

A colleague of mine asked me today "how do I line break my resource string? Enter doesn't work". This is when I realized that this thing wasn't as trivial as one may think...

So how do you that? In resources and string properties on the designer in Visual Studio, you can see only one line at a time and when you hit Enter, the value is set and you don't get the required line break.

All you have to do in order to have your line break, is hit Shift + Enter. This will break the line and put the cursor at the beginning of the next line.

image

Hope it helps,
Shay.

Posted by shayf | 1 comment(s)

Dynamic Languages and The .Net Framework - Promo #2

This is the second promo post to my session at Developer Academy III. The rest of the series:

Now to the post...

The Task: Retrieve a value without the necessity to lose the type benefits.

Sometimes you want to a method to retrieve a value from somewhere. C# offers you a few solutions - you can return object, you can return a class (or struct) that has StringValue, IntValue, DateValue and so on properties (I've seen this solution too many times), you can create a generic return type that involves reflection (I've written a post about that on my old blog) or you can create several different methods.
All of the above solutions will work for sure, but what if you could write:

---- IronRuby code ----

def get_value(key)
    case key
    when :StringValue
        return "Hello World"
    when :IntValue
        return 10
    when :FloatValue
        return 1.618
    end
end

puts "StringValue: " + get_value(:StringValue)
puts "IntValue: " + (get_value(:IntValue) * 5).to_s
puts "FloatValue: " + (get_value(:FloatValue) - 1).to_s

---------------------------

The output you'll get is:

StringValue: Hello World
IntValue: 50
FloatValue: 0.618

It can be as simple and intuitive as that... and it's just at the tip of your finger!
The next post in the series will take this one step even further, stay tuned!

Haven't had enough? come to my session at Developer Academy III! :)

All the best,
Shay.

Posted by shayf | with no comments

Dynamic Languages and The .Net Framework - Promo #1

This is the first post of a promo series to my session at the upcoming Developer Academy III conference - Dynamic Languages and The .Net Framework. In the series, I'm going to explore some of the reasons that made me fall in love with this type of programming languages.

Let's start...

Why waste keyboard clicks?

The task: Write to the console the numbers from 1 to 10.

C#

using System;

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            for (int i = 1; i <= 10; i++) { Console.WriteLine(i); }
        }
    }
}

VB.Net

Module Module1
    Sub Main()
        For i As Integer = 1 To 10
            Console.WriteLine(i)
        Next
    End Sub
End Module

IronRuby

(1..10).each { |i| puts i }

Want it only from 1 to 9, just add another dot between 1 and 10 --> (1...10).each...

IronPython

for i in range(1,11): print i

All of the above code pieces print the exact same output to the console.

WOW!

Haven't had enough? come to my session at Developer Academy III! :)

All the best,
Shay.

Posted by shayf | with no comments

My Dev Academy III Session - Dynamic Languages and the .Net Framework

Hi all,

I'm going to pass a session about Dynamic Languages and the .Net Framework in the upcoming Dev Academy conference.

I'm very excited about that and I'm working very hard to deliver you a fun, fresh and informative session!

So remember to register to the event and make sure to come to my session!

Developer Academy 3

Links:
Dev Academy III site
Dev Academy Twitter account

See you there!
Shay.

Posted by shayf | with no comments

.Net Tip: Get and Set The User's Keyboard Layouts

Have you ever wanted to know what keyboard layouts are installed on your user's host? Have you ever wanted to set the keyboard layout in your form? .Net makes it easy for you!

How do you do that? here it is:

Get the installed layouts:

foreach (InputLanguage layout in InputLanguage.InstalledInputLanguages)
{
  Console.WriteLine(layout.LayoutName);
}

Set the layout

// This will set the keyboard layout to Hebrew
InputLanguage.CurrentInputLanguage = InputLanguage.FromCulture(new System.Globalization.CultureInfo("he"));

The InputLanguage class is very handy in some cases, use it!

All the best,
Shay

Posted by shayf | with no comments