Thomas 的个人资料Blogs日志列表 工具 帮助
9月27日

Compiling and running a dynamic method at runtime

This issue might be very useful, for instance if you need to perform an expression for each item in a list, that is depending on the user's input. instead of writing a static method, that is handling all possibilites with conditions like
"if (flag_set) {}", it's possible to dynamically create a small C# source code that is optimized for that special purpose, compile it and simply use it whilst enumerating the list.

the following link shows the way:
http://www.codeproject.com/cs/algorithms/matheval.asp


9月22日

Compression and Decompression

For compressing/decompressing purposes of bytes, .NET 2.0 offers functionality for it.
You can either use the DeflateStream class or the GZipStream class, both available in the
System.IO.Compression assembly. See the MSDN for further information.

9月14日

Example: Draw a gradiented background for a panel:

private void XDTFind_OnPaintPanel(object sender, PaintEventArgs e)
{
    Rectangle r = this.PanelRectangle;
    Brush b;

    if (searchPanel.ContainsFocus)
    {
        b = new LinearGradientBrush(
        ClientRectangle,
        Color.Gold,
        Color.Orange,
        LinearGradientMode.Vertical);

    }
    else
    {
        b = new LinearGradientBrush(
        ClientRectangle,
        Color.LightSteelBlue,
        Color.Lavender,
        LinearGradientMode.ForwardDiagonal);
    }
    e.Graphics.FillRectangle(b, r);
}


9月11日

Remoting

Remoting describes how to call methods on a server using the tcp protocoll:

http://www.microsoft.com/germany/msdn/nettv/folge1.mspx#EAC

Connection to a web service (the simplest way):

Accessing to an existing web service in .NET is as easy as it can be:

Remember the previous generated web service that has the following members
  • int Count();
  • string Merge(string a, string b);

Now let the service run in the background and create a new form application. Then, In the solution explorer you select "Add new web Reference..." from the context menu.

In the dialog, type in the url adress of the running web service (in this example it's "http://localhost:1122/WebSite2" and then you'll see the directory list, where you select "service.asmx" and then you finally need to click the button "Add Reference" and a new file "localhost" is added to your form project in the Web References section on the solution explorer.

Now you can simply access all methods of the web services as simple as accessing to properties of an object. See a simply example here:

 
    private void button1_Click(object sender, EventArgs e)
    {
        /// Create the web service client here:
        Service service = new Service();
 
        /// Call a method form the web service.
        /// Note that this method uses SOAP to post the params to the server and for receving the result.
        string s = service.Merge("This is a Test", "123");
        MessageBox.Show(s);
    }
 


That' all!

So within one minute, you can access all methods of an existing web service.

By the way, the web reference  (in this example  named  localhost)  provides  2 method access  members for each method on the web service:

  • a synchrone acess that waits until the method has executed
  • a n asynchrone acess that starts the method but doesn't wait for it to be executed.
So despite the service.Merge() method, there is also a service.MergeAsync() method. For receiving the result of a method, an event handler can be added for each method, which looks like this:



        
	private void button1_Click(object sender, EventArgs e)
        {
            Service service = new Service();
 
              /// Add an event that occures when the web service has finished to process the
              /// Merge() method:
            service.MergeCompleted += new MergeCompletedEventHandler(service_MergeCompleted);
 
             /// now executhe the Merge method asynchronously:
            service.MergeAsync("This is a Test", "123");
        }
 
         /// <summary>
        /// Raises, when the web service's Merge() method has completed:
         /// </summary>
        void service_MergeCompleted(object sender, MergeCompletedEventArgs e)
        {
            /// Display the result of the Merge() method specified in the EventArgs:
            MessageBox.Show(e.Result);
        }
 




9月7日

Lists, arrays and collections.

Sometimes you need to build a class that requires a property that holds several objects of the same type.
 
Intuitively, you'd choose a generic List<myobject> type for the property, but thats not the optimal choice.
Because using a List means that the list must be previousely created with several List.Add() calls. But sometimes it could be easier to create a simple ObjectType[] array like
Button[] = {button1,button2,button3}
if the objects for the list are constant and only a view.
This is much more shorter than
List<Button> list = new List<Button();
list.Add(button1);
list.Add(button2);
list.Add(bitton3);
To offer both possibilites, simply don't specify List<> as the property type rather than ICollection<>, as both List<myobject> and myobject[] have implemented the ICollection<myObject>.
 
So finally we come to the conclusion:
 
Prefer to specify ICollection<myobject> as a property type rather than List<myobject>.
 
9月5日

Creating a Web Client to access a previousely created Web Service

After creating our first web service, we are no prepared to access it's members using HTML Post functionality, which goes like this:

private void button1_Click(object sender, EventArgs e)
{
    WebClient client = new WebClient();
    client.UseDefaultCredentials = true;
    client.Encoding = System.Text.Encoding.UTF8;
    client.Headers.Add("Authorization", "Basic wqoieuoqwenand,asdn");
    NameValueCollection values = new NameValueCollection();
    values.Add("a", "VR");
    values.Add("b", "Developers!");
    byte[] result = client.UploadValues("http://localhost:1882/WebSite1/Service.asmx/Merge", values);
    string value = System.Text.Encoding.ASCII.GetString(result);
    textBox1.Text = value;
}


As you see, the two params for the Merge member are specified in a NameValueCollection class, while the HttpPost is done by calling WebClient.UploadValues which returns a byte[] value, that represents an xml string that looks like followed:

<?xml version="1.0 encoding="utf-8"?><string xmlns="http://tempuri.rog/">Merged VR with Developpers!</string>

Of course you'll have to to some additional stuff, but this is the simple way to access a web service in .NET.

Note that the 1882 port may differ, so you might change it. Just click on the tool tray icon of the running web service to see it's current port number.

Creating a Web Service in .NET

Creating a simple web service within Visual Studio 2005 is done in a view minutes:

  1. From the File Menu select New->Web Site..
  2. Choose ASP.NET Web Service (ensure the language to be set to C# or your prefered language)
  3. Now you already have a Web Service with a HelloWorld member that can be accessed with Html Post or Soap to return the "Hello World" string.
  4. Now you want to create a member, having some params, called Merge, wich finally looks like this:


[WebService(Namespace = "http://www.tomsblog.de/", Description = "For testing purposes only")]
[WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
public class Service : System.Web.Services.WebService
{
    private int counter = 0;
    public Service ()
    {
    }
 
    [WebMethod(Description="Returns a counter value as string")]
    public string Counter()
    {
        counter++ return counter.ToString();
    } 
    [WebMethod(Description="Merges to strings to one.")]
    public string Merge(string a, string b)
    {
        return a + " and " + b;
    }
}



The Merge member requires 2 string params.

Now you know how to access the web service and how to create a web client comes with the next blog...



Encryption and Decryption of string

For some circumstances, you might need to encrypt a string and later decrypt it, using a symmetric key. This is an examply, how to easily do this with less effords:



    private void button1_Click(object sender, EventArgs e)
    {
        string XmlKey = "<RSAKeyValue><Modulus>qcI3yc5NlFI6Kk0IhlhZARDVBd1OTXHNekKzVv4oQGAYW/6EX+CbCj0oFszVcwCx1W9UloxjL5SVqs16It041C9wJWOHoXk3rcY3FsHg3Tt/zSrmPlNdB5Hm3CJj4TbEgcYF51C09clor+f8NFf9OXpYAVlgBhw7tUd5upVFWxM=</Modulus><Exponent>AQAB</Exponent><P>3L6a8u3jThDJsSui8k0pA6+KG+8lPoabmrrjN/cBQsj9qXQjB5J9AXrh7wjysm3SiY4VAGad9dK8vnixgsDjJQ==</P><Q>xN7++uCNoegB39FnsjRXsHa6Ls+gKAs5YT0fpW4+53IAXkfho0qFLMZgoIywPZ6mXlX7g6OQn4XJgxrgeDQL1w==</Q><DP>yh8c8eMwhoKIq1kxUnukWmOZKgrHJ4FJaVxGQTBCT0yKN2bHzF8tZvWFesHOt+InLRyTzlInwLa9bApHP1ouoQ==</DP><DQ>md3DoSZh67mdxWUvy4q3Qlb42t8xSDrFhOc11aDdjxx9hzJc+reicEU3fiOXFwHo+2/uHIt43AS/YzVdXPUojw==</DQ><InverseQ>AFIvV1J9WwSFpWeS7RTrnz8oE3mg3+xMoV5uUK4zY7zDCnnNek9Ds6NC20GNx3pACnTgARsDpo0Urc2p6wgtfQ==</InverseQ><D>KDtrVVybbkd+mX/gQVa24VXH5rfoUtphxFQChN9/UqJzo3nSjZaBqA+ObLjm7XaArwDPn05uQ1yHjA9entynFt+dwoeH+ETOrnXG6BAeBaPeSF43fKVCEx8NmFiNsEV0YdC7WgfMAmQHGBcXV+a2XC1ZZP5qdcX2GbLgNUc9QCe=</D></RSAKeyValue>";

         /// Create the RSA provider for encryption/decryption:
        RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
 
        /// set the symmetric key from an xml string:
        /// Note, that without specifying a key, a random key is automatically created.
        /// You may save the currently used key with rsa.ToXmlString().
        rsa.FromXmlString(XmlKey);
        byte[] bytes = Encoding.ASCII.GetBytes(textBox2.Text);
        byte[] encrypted = rsa.Encrypt(bytes, false);
        /// to display the encrypted data as a string, the BitConverter does a 
        /// very neat job:
        string value = BitConverter.ToString(encrypted);
        textBox1.Text = value;
 
        /// now decrypt the encrypted bytes[] and convert it into a readable string:
        /// Note, that actually, it would become necassary to build the byte[] buffer
        /// with the encrypted data from eg the hex reprentation of BitConverter.ToString(),
        /// but for this cases it's no interesting point.
        bytes = rsa.Decrypt(encrypted, false);
        value = Encoding.ASCII.GetString(bytes);
        textBox3.Text = value;
    }



Of course there are also other possibilties in .NET that might be more accurate for the purpose, like the class EncrytpedXml which is specialized for xml encryption, or take a look at the System.Security.Cryptography namespaces to explorer a varity of different symetric and asymetric encryption classes like DES, RAS, Rijandel and also common hashing algorithms like the commonly known MD5.