Initiera objekt på en rad - Object initializer
2009-02-13 11:58 - Utvecklingstips av Christian Landgren
Christian Landgren
Systemutvecklare
Iteam
Ursäkta för det dåliga bildskämtet – initiera en klass = första dagen i en skolklass.. ;-)
För en tid sedan skrev jag en blogg om det enklaste exemplet för integration mot Exchange. Då hade jag ännu inte lärt mig en ny teknik i C# 3.0 som heter Object initializer. Object initializer gör att man kan både initiera ett objekt och tilldela dess egenskaper på samma rad, detta är en gammal nyhet egentligen men många känner inte till den så här kommer lite bakgrundsinformation om varför den är så bra att känna till. Med hjälp av den tekniken så slipper man initiera temporära variabler för alla initieringsobjekt. Koden som produceras liknar ganska mycket JavaScript där man ofta använder detta för att skicka parametrar till metoder med hjälp av temporära objekt.
Du intierar objektet genom att lägga till {} efter din objektintiering ().
new User() { Email = "John" }
Störst effekt gör detta när man använder sig av Web Services, för problemet med SOAP Web Services är att det inte går att definiera konstruktorer på serversidan. Man måste manuellt skapa temporära objekt vilket i tidigare versioner av C# behövde göras på flera rader vilket tog lite mycket visuell plats i koden. Exchange Web Service är typiskt exempel där det här ger enorm effekt.
Exempel på kod som initieras på flera rader:
User user = newUser();
user.FirstName = "John";
user.LastName = "Doe";
user.Email = new EmailAddress();
user.Email.Address = "john@doe.com";
user.Email.Name ="John Doe";
Users.Add(user);
Kan nu skrivas såhär:
Users.Add(newUser() { Email = newEmailAddress() { Address="john@doe.com", Name="John Doe"}, FirstName ="John", LastName = "Doe"});
Dessutom får man ypperlig hjälp av Intellisence som också kommer ihåg vilka objekt du redan har angett. Lägg också märke till att du kan intiera fler objekt inne i initieraren.

Med hjälp av den här tekniken blir det kortaste Exchange kodexemplet så här "kort":
using exchange; // your namespace to the webservice
using System.Security.Principal;
// server = ex. https://exchange-server
// exchangeCredentials är det konto som du vill hämta tasks från eller ett servicekonto – då anger du en mailbox i folders nedan
publicList<TaskType> GetOutlookTasks(string serverUrl, System.Net.NetworkCredential exchangeCredentials)
{
ExchangeServiceBinding esb = new ExchangeServiceBinding() { Credentials = exchangeCredentials, Url =string.Format(@"{0}/EWS/Exchange.asmx", serverUrl) }; // Tell it you only want to look in the tasks folder
DistinguishedFolderIdType[] folders = { newDistinguishedFolderIdType() { Id = DistinguishedFolderIdNameType.tasks }}; // Form the FindItem request
FindItemType findItemRequest = new FindItemType() { ItemShape = new ItemResponseShapeType() { BaseShape =DefaultShapeNamesType.AllProperties }, ParentFolderIds = folders }; // Send the request and get the response
FindItemResponseType findItemResponse = esb.FindItem(findItemRequest);
if (findItemResponse.ResponseMessages.Items.Length > 0)
{
// Detta skulle man gärna slippa...
ArrayOfRealItemsType realItems = ((FindItemResponseMessageType)(findItemResponse.ResponseMessages.Items[0])).RootFolder.Itemas ArrayOfRealItemsType;
List<TaskType> outlookTasks = new List<TaskType>();
foreach (TaskType task in realItems.Items)
{
// smidigt att kunna anropa fälten direkt mha Intellisence och utan krångliga schemanamn etc
Console.WriteLine("Task: {0} Duration: {1}-{2} \n", task.Subject, task.StartDate, task.DueDate);
outlookTasks.Add(task);
}
return outlookTasks;
}
return null;
}
... och du vet väl att Iteam just nu söker duktiga medarbetare? Läs mer på iteam.se
Andra bloggar om:
C#,
Web Services