Monday, May 30, 2011

C# Build Macros for use inside Build Events

Macro

Description

$(ConfigurationName)

The name of the current project configuration, for example, "Debug|Any CPU".

$(OutDir)

Path to the output file directory, relative to the project directory. This resolves to the value for the Output Directory property. It includes the trailing backslash '\'.

$(DevEnvDir)

The installation directory of Visual Studio 2005 (defined with drive and path); includes the trailing backslash '\'.

$(PlatformName)

The name of the currently targeted platform. For example, "AnyCPU".

$(ProjectDir)

The directory of the project (defined with drive and path); includes the trailing backslash '\'.

$(ProjectPath)

The absolute path name of the project (defined with drive, path, base name, and file extension).

$(ProjectName)

The base name of the project.

$(ProjectFileName)

The file name of the project (defined with base name and file extension).

$(ProjectExt)

The file extension of the project. It includes the '.' before the file extension.

$(SolutionDir)

The directory of the solution (defined with drive and path); includes the trailing backslash '\'.

$(SolutionPath)

The absolute path name of the solution (defined with drive, path, base name, and file extension).

$(SolutionName)

The base name of the solution.

$(SolutionFileName)

The file name of the solution (defined with base name and file extension).

$(SolutionExt)

The file extension of the solution. It includes the '.' before the file extension.

$(TargetDir)

The directory of the primary output file for the build (defined with drive and path). It includes the trailing backslash '\'.

$(TargetPath)

The absolute path name of the primary output file for the build (defined with drive, path, base name, and file extension).

$(TargetName)

The base name of the primary output file for the build.

$(TargetFileName)

The file name of the primary output file for the build (defined as base name and file extension).

$(TargetExt)

The file extension of the primary output file for the build. It includes the '.' before the file extension.

Sunday, May 29, 2011

WCF Architecture Diagram

Visual Studio 2010 Certification Paths

Microsoft Certified Technology Specialist (MCTS)

MCTS certifications provide the foundation for Microsoft Certification. These certifications are designed to help validate your skills on the features and functionality of key technologies. You can show your depth of knowledge in one specific technology, earn multiple MCTS certifications to show breadth across different technologies, or build on the MCTS to earn one of our Microsoft Certified Professional Developer (MCPD) certifications.

Your goal

Certification

Requirements

To create Windows-based applications that run on corporate servers or user desktop computers.

MCTS: .NET Framework 4, Windows Applications

Exam 70-511: TS: Windows Applications Development with Microsoft .NET Framework 4

To create web-based applications that run on the ASP.NET platform and are hosted on Internet Information Server.

MCTS: .NET Framework 4, Web Applications

Exam 70-515: TS: Web Applications Development with Microsoft .NET Framework 4

To create applications that communicate with servers or other applications in a connected or disconnected state.

MCTS: .NET Framework 4, Service Communication Applications

Exam 70-513: TS: Windows Communication Foundation Development with Microsoft .NET Framework 4

To create data-driven applications that access data from various sources, such as Microsoft SQL Server, Oracle, Microsoft Office Access, object data sources, XML, or other flat-file sources.

MCTS: .NET Framework 4, Data Access

Exam 70-516: TS: Accessing Data with Microsoft .NET Framework 4

To create rich Internet-based applications by using Microsoft Silverlight.

MCTS: Silverlight 4, Development

Exam 70-506: TS: Silverlight 4, Development

Microsoft Certified Professional Developer (MCPD)

MCPD certifications help validate a comprehensive set of skills that are necessary to design, build, and deploy applications successfully by using Microsoft Visual Studio and the Microsoft .NET Framework. This certification builds on the MCTS certification and is designed to help provide hiring managers with a strong indicator of your potential job success. Candidates for the MCPD typically have two to three years of relevant experience and a commitment to remaining current in best practices and technologies.

Your goal

Certification

Certification prerequisites

Requirements

To design, build, and deploy Windows-based applications by using Visual Studio 2010.

MCPD: Windows Developer 4

MCTS: .NET Framework 4, Windows Applications

and

MCTS: .NET Framework 4, Service Communication Applications

and

MCTS: .NET Framework 4, Data Access

Exam 70-518: PRO: Designing and Developing Windows Applications Using Microsoft .NET Framework 4

To design, build, and deploy web-based applications by using Visual Studio 2010.

MCPD: Web Developer 4

MCTS: .NET Framework 4, Web Applications

and

MCTS: .NET Framework 4, Service Communication Applications

and

MCTS: .NET Framework 4, Data Access

Exam 70-519: PRO: Designing and Developing Web Applications Using Microsoft .NET Framework 4

To design, build, and deploy cloud-based applications that will be hosted on Windows Azure.

MCPD: Windows Azure Developer

MCTS: .NET Framework 4, Service Communication Applications

and

MCTS: .NET Framework 4, Data Access

Exam 70-583: PRO: Designing and Developing Windows Azure Applications*

Oracle Certification Path

SQL Server 2008 Certification Path


Microsoft Certified Technology Specialist -

Your profile

Certification

Exam

Working with SQL Server 2008 and performing database administrator tasks: installing, configuring, and maintaining

MCTS: SQL Server 2008, Implementation and Maintenance

Exam 70-432: TS: Microsoft SQL Server 2008, Installation and Maintenance

Note This exam is also required for the MCITP: Database Administrator 2008 certification.

Working with SQL Server 2008 and writing application code against systems that run SQL Server 2008, writing T-SQL or Microsoft .NET CLR code that runs inside SQL Server 2008, or developing solutions in SQL Server 2008

MCTS: SQL Server 2008, Database Development

Exam 70-433: TS: Microsoft SQL Server 2008, Database Development

Note This exam is also required for the MCITP: Database Developer 2008 certification.

Working with SQL Server 2008 and working with the business intelligence technologies, including Reporting Services, Analysis Services, and Integration Services

MCTS: SQL Server 2008, Business Intelligence Development and Maintenance

Exam 70-448: TS: Microsoft SQL Server 2008, Business Intelligence Development and Maintenance

Note This exam is also required for the MCITP: Business Intelligence Developer 2008 certification.

Friday, May 27, 2011

Converting AdomdClient.CellSet to Ado DataSet

private DataTable ConvertCellSetToDataSet(CellSet cs)
{
DataTable dt = new DataTable();
DataColumn dc = null;
DataRow dr = null;

//add the columns
//
//first column
dt.Columns.Add(new DataColumn(" "));
string name = null;
StringBuilder builder = null;
//get the other columns from axis
foreach (var pos in cs.Axes[0].Positions)
{
dc = new DataColumn();
builder = new StringBuilder();
foreach (var mem in pos.Members)
{
// Decide how you want to display your colum and row headers when multiple dimensions to be displayed. The sample code appends a : between columns and rows
builder.AppendFormat("{0} : ", mem.Caption);
}
if (builder.Length > 0)
builder.Length -= 5;

dc.ColumnName = builder.ToString();
dt.Columns.Add(dc);
}

//add each row, row label first, then data cells
int y = 0;
foreach (var py in cs.Axes[1].Positions)
{
dr = dt.NewRow();
//create new row
// Do the row label
builder = new StringBuilder();
foreach (var mem in py.Members)
{
builder.AppendFormat("{0} : ", mem.Caption);
}
if (builder.Length > 0)
builder.Length -= 5;

dr[0] = builder.ToString();
//first cell in the row

// Data cells
int x = 0;
for (x = 0; x <= cs.Axes[0].Positions.Count - 1; x++)
{
dr[x + 1] = cs[x, y].FormattedValue;
//other cells in the row
}

dt.Rows.Add(dr);
//add the row
y = y + 1;
}

return dt;
}

Deserialzing XML With Validation

Many of the times we come across situations we have an XML file as input from the customer.
We need to:
1. Validate the XML against a known schema
2. Deserialize it into a known object

1. To validate the XML against a known schema, we should either have a pre-existing schema, which has been already provided to you, or you have to create a schema based on the sample XML file. Be careful, that your XML file will cover all the cases against which the schema has to be evaluated.
Example of creating a schema by the xml file using XSD Tool:
At the VS command prompt type: -->xsd AdhocTestCases.xml
The above command generates an ouput xml schema as AdhocTestCases.xsd which you can use for validation of the user XML.

2. Create a known .NET object that you can use to in the application to manipulate the XML file a shown:
xsd AdhocTestCases.xml
xsd AdhocTestCases.xsd /c
The above command generates an AdhocTestCases.cs class [use /c /l:vb for vb class file] for the corresponding schema. All the schema elements would be mapped to properties in the resultant class.

The Actual conversion
1. Loading the Schema to a stream
If you have a schema available at the output directory or at some other location, you can obtain the stream for that particular xsd using any of the IO classes (For example, FileStream).
Stream stream = File.OplenRead(locationOfTheFile);

If you have the schema as an embedded resource in the assembly
// Build Action = Embedded Resource
// Copy To Output Directory = Do not Copy
XmlSchemaSet schema = new XmlSchemaSet();
Stream stream= Assembly.GetExecutingAssembly().GetManifestResourceStream("XmlReport.ReportSchmea.xsd");


2. Create a reader settings specifying the type of
XmlReaderSettings settings = new XmlReaderSettings();
settings.Schemas.Add(null, XmlReader.Create(stream));
settings.ValidationType = ValidationType.Schema;
settings.ValidationEventHandler += new ValidationEventHandler(ValidationCallBack);

3. Open the XML and specify the settings which contain the schema
XmlReader reader = XmlReader.Create("AdhocTestCases.xml", settings);

4. Try to desrerialize the type into the object of type xsd
XmlSerializer serialize = new XmlSerializer(typeof(ReportTestDefinition));
definition= (ReportTestDefinition)serialize.Deserialize(reader);

5. Implement ValidationEventHanlder
You can optionally implement the ValidationEventHandler on the XmlReaderSettings class to specifying some clean up if required or posting the error information.

private static void ValidationCallBack (object sender, ValidationEventArgs args) {
if (args.Severity==XmlSeverityType.Warning)
Console.WriteLine("\tWarning: Matching schema not found. No validation occurred." + args.Message);
else
Console.WriteLine("\tValidation error: " + args.Message);
}

String Formatting

Integer numbers can be formatted in .NET in many ways. You can use static method String.Format or instance method int.ToString. Following examples shows how to align numbers (with spaces or zeroes), how to format negative numbers or how to do custom formatting like phone numbers.

Add zeroes before number
To add zeroes before a number, use colon separator „:“ and write as many zeroes as you want.

String.Format("{0:00000}", 15); // "00015"
String.Format("{0:00000}", -15); // "-00015"

Align number to the right or left
To align number to the right, use comma „,“ followed by a number of characters. This alignment option must be before the colon separator.

String.Format("{0,5}", 15); // " 15"
String.Format("{0,-5}", 15); // "15 "
String.Format("{0,5:000}", 15); // " 015"
String.Format("{0,-5:000}", 15); // "015 "

Different formatting for negative numbers and zero
You can have special format for negative numbers and zero. Use semicolon separator „;“ to separate formatting to two or three sections. The second section is format for negative numbers, the third section is for zero.

String.Format("{0:#;minus #}", 15); // "15"
String.Format("{0:#;minus #}", -15); // "minus 15"
String.Format("{0:#;minus #;zero}", 0); // "zero"

Custom number formatting (e.g. phone number)
Numbers can be formatted also to any custom format, e.g. like phone numbers or serial numbers.

String.Format("{0:+### ### ### ###}", 447900123456); // "+447 900 123 456"
String.Format("{0:##-####-####}", 8958712551); // "89-5871-2551"


String Format for Double
The following examples show how to format float numbers to string in C#. You can use static method String.Format or instance methods double.ToString and float.ToString.
Digits after decimal point
This example formats double to string with fixed number of decimal places. For two decimal places use pattern „0.00“. If a float number has less decimal places, the rest digits on the right will be zeroes. If it has more decimal places, the number will be rounded.

// just two decimal places
String.Format("{0:0.00}", 123.4567); // "123.46"
String.Format("{0:0.00}", 123.4); // "123.40"
String.Format("{0:0.00}", 123.0); // "123.00"

Next example formats double to string with floating number of decimal places. E.g. for maximal two decimal places use pattern „0.##“.

// max. two decimal places
String.Format("{0:0.##}", 123.4567); // "123.46"
String.Format("{0:0.##}", 123.4); // "123.4"
String.Format("{0:0.##}", 123.0); // "123"

Digits before decimal point
If you want a float number to have any minimal number of digits before decimal point use N-times zero before decimal point. E.g. pattern „00.0“ formats a float number to string with at least two digits before decimal point and one digit after that.

// at least two digits before decimal point
String.Format("{0:00.0}", 123.4567); // "123.5"
String.Format("{0:00.0}", 23.4567); // "23.5"
String.Format("{0:00.0}", 3.4567); // "03.5"
String.Format("{0:00.0}", -3.4567); // "-03.5"

Thousands separator
To format double to string with use of thousands separator use zero and comma separator before an usual float formatting pattern, e.g. pattern „0,0.0“ formats the number to use thousands separators and to have one decimal place.

String.Format("{0:0,0.0}", 12345.67); // "12,345.7"
String.Format("{0:0,0}", 12345.67); // "12,346"

Zero
Float numbers between zero and one can be formatted in two ways, with or without leading zero before decimal point. To format number without a leading zero use # before point. For example „#.0“ formats number to have one decimal place and zero to N digits before decimal point (e.g. „.5“ or „123.5“).
Following code shows how can be formatted a zero (of double type).

String.Format("{0:0.0}", 0.0); // "0.0"
String.Format("{0:0.#}", 0.0); // "0"
String.Format("{0:#.0}", 0.0); // ".0"
String.Format("{0:#.#}", 0.0); // ""

Align numbers with spaces
To align float number to the right use comma „,“ option before the colon. Type comma followed by a number of spaces, e.g. „0,10:0.0“ (this can be used only in String.Format method, not indouble.ToString method). To align numbers to the left use negative number of spaces.

String.Format("{0,10:0.0}", 123.4567); // " 123.5"
String.Format("{0,-10:0.0}", 123.4567); // "123.5 "
String.Format("{0,10:0.0}", -123.4567); // " -123.5"
String.Format("{0,-10:0.0}", -123.4567); // "-123.5 "

Custom formatting for negative numbers and zero
If you need to use custom format for negative float numbers or zero, use semicolon separator„;“ to split pattern to three sections. The first section formats positive numbers, the second section formats negative numbers and the third section formats zero. If you omit the last section, zero will be formatted using the first section.

String.Format("{0:0.00;minus 0.00;zero}", 123.4567); // "123.46"
String.Format("{0:0.00;minus 0.00;zero}", -123.4567); // "minus 123.46"
String.Format("{0:0.00;minus 0.00;zero}", 0.0); // "zero"

Some funny examples
As you could notice in the previous example, you can put any text into formatting pattern, e.g. before an usual pattern „my text 0.0“. You can even put any text between the zeroes, e.g. „0aaa.bbb0“.

String.Format("{0:my number is 0.0}", 12.3); // "my number is 12.3"
String.Format("{0:0aaa.bbb0}", 12.3); // "12aaa.bbb3"

String Format for DateTime
This example shows how to format DateTime using String.Format method. All formatting can be done also using DateTime.ToString method.

Custom DateTime Formatting
There are following custom format specifiers y (year), M (month), d (day), h (hour 12), H (hour 24), m (minute), s (second), f (second fraction), F (second fraction, trailing zeroes are trimmed),t (P.M or A.M) and z (time zone).
Following examples demonstrate how are the format specifiers rewritten to the output.

// create date time 2008-03-09 16:05:07.123
DateTime dt = new DateTime(2008, 3, 9, 16, 5, 7, 123);

String.Format("{0:y yy yyy yyyy}", dt); // "8 08 008 2008" year
String.Format("{0:M MM MMM MMMM}", dt); // "3 03 Mar March" month
String.Format("{0:d dd ddd dddd}", dt); // "9 09 Sun Sunday" day
String.Format("{0:h hh H HH}", dt); // "4 04 16 16" hour 12/24
String.Format("{0:m mm}", dt); // "5 05" minute
String.Format("{0:s ss}", dt); // "7 07" second
String.Format("{0:f ff fff ffff}", dt); // "1 12 123 1230" sec.fraction
String.Format("{0:F FF FFF FFFF}", dt); // "1 12 123 123" without zeroes
String.Format("{0:t tt}", dt); // "P PM" A.M. or P.M.
String.Format("{0:z zz zzz}", dt); // "-6 -06 -06:00" time zone

You can use also date separator / (slash) and time sepatator : (colon). These characters will be rewritten to characters defined in the current DateTimeFormatInfo.DateSeparator and DateTimeFormatInfo.TimeSeparator.

// date separator in german culture is "." (so "/" changes to ".")
String.Format("{0:d/M/yyyy HH:mm:ss}", dt); // "9/3/2008 16:05:07" - english (en-US)
String.Format("{0:d/M/yyyy HH:mm:ss}", dt); // "9.3.2008 16:05:07" - german (de-DE)

Here are some examples of custom date and time formatting:
// month/day numbers without/with leading zeroes
String.Format("{0:M/d/yyyy}", dt); // "3/9/2008"
String.Format("{0:MM/dd/yyyy}", dt); // "03/09/2008"

// day/month names
String.Format("{0:ddd, MMM d, yyyy}", dt); // "Sun, Mar 9, 2008"
String.Format("{0:dddd, MMMM d, yyyy}", dt); // "Sunday, March 9, 2008"

// two/four digit year
String.Format("{0:MM/dd/yy}", dt); // "03/09/08"
String.Format("{0:MM/dd/yyyy}", dt); // "03/09/2008"

Standard DateTime Formatting
In DateTimeForma¬tInfo there are defined standard patterns for the current culture. For example property ShortTimePattern is string that contains value h:mm tt for en-US culture and value HH:mm for de-DE culture.
Following table shows patterns defined in DateTimeForma¬tInfo and their values for en-US culture. First column contains format specifiers for the String.Format method.
Specifier DateTimeFormatInfo property Pattern value (for en-US culture)
t ShortTimePattern h:mm tt
d ShortDatePattern M/d/yyyy
T LongTimePattern h:mm:ss tt
D LongDatePattern dddd, MMMM dd, yyyy
f (combination of D and t) dddd, MMMM dd, yyyy h:mm tt
F FullDateTimePattern dddd, MMMM dd, yyyy h:mm:ss tt
g (combination of d and t) M/d/yyyy h:mm tt
G (combination of d and T) M/d/yyyy h:mm:ss tt
m, M MonthDayPattern MMMM dd
y, Y YearMonthPattern MMMM, yyyy
r, R RFC1123Pattern ddd, dd MMM yyyy HH':'mm':'ss 'GMT' (*)
s SortableDateTi¬mePattern yyyy'-'MM'-'dd'T'HH':'mm':'ss (*)
u UniversalSorta¬bleDateTimePat¬tern yyyy'-'MM'-'dd HH':'mm':'ss'Z' (*)
(*) = culture independent
Following examples show usage of standard format specifiers in String.Format method and the resulting output.

String.Format("{0:t}", dt); // "4:05 PM" ShortTime
String.Format("{0:d}", dt); // "3/9/2008" ShortDate
String.Format("{0:T}", dt); // "4:05:07 PM" LongTime
String.Format("{0:D}", dt); // "Sunday, March 09, 2008" LongDate
String.Format("{0:f}", dt); // "Sunday, March 09, 2008 4:05 PM" LongDate+ShortTime
String.Format("{0:F}", dt); // "Sunday, March 09, 2008 4:05:07 PM" FullDateTime
String.Format("{0:g}", dt); // "3/9/2008 4:05 PM" ShortDate+ShortTime
String.Format("{0:G}", dt); // "3/9/2008 4:05:07 PM" ShortDate+LongTime
String.Format("{0:m}", dt); // "March 09" MonthDay
String.Format("{0:y}", dt); // "March, 2008" YearMonth
String.Format("{0:r}", dt); // "Sun, 09 Mar 2008 16:05:07 GMT" RFC1123
String.Format("{0:s}", dt); // "2008-03-09T16:05:07" SortableDateTime
String.Format("{0:u}", dt); // "2008-03-09 16:05:07Z" UniversalSortableDateTime


IFormatProvider for Numbers
This example shows how to convert float to string and string to float using IFormatProvider. To get IFormatProvider you need to get CultureInfo instance first.
Get invariant or specific CultureInfo
Invariant culture is a special type of culture which is culture-insensitive. You should use this culture when you need culture-independent results, e.g. when you format or parse values in XML file. The invariant culture is internally associated with the English language. To get invariant CultureInfo instance use static property CultureInfo.In¬variantCulture.
To get specific CultureInfo instance use static method CultureInfo.Get¬CultureInfo with the specific culture name, e.g. for the German language CultureInfo.GetCultureInfo("de-DE").
Format and parse numbers using the IFormatProvider
Once you have the CultureInfo instance use property CultureInfo.Num¬berFormat to get anIFormatProvider for numbers (the NumberFormatInfo object)

// format float to string
float num = 1.5f;
string str = num.ToString(CultureInfo.InvariantCulture.NumberFormat); // "1.5"
string str = num.ToString(CultureInfo.GetCultureInfo("de-DE").NumberFormat); // "1,5"

// parse float from string
float num = float.Parse("1.5", CultureInfo.InvariantCulture.NumberFormat);
float num = float.Parse("1,5", CultureInfo.GetCultureInfo("de-DE").NumberFormat);


Custom IFormatProvider
The following example shows how to write a custom IFormatProvider which you can use in method String.Format(I¬FormatProvider, …).
This formatter formats doubles to 3 decimal places with a dot separator.

public class DoubleFormatter : IFormatProvider, ICustomFormatter
{
// always use dot separator for doubles
private CultureInfo enUsCulture = CultureInfo.GetCultureInfo("en-US");

public string Format(string format, object arg, IFormatProvider formatProvider)
{
// format doubles to 3 decimal places
return string.Format(enUsCulture, "{0:0.000}", arg);
}

public object GetFormat(Type formatType)
{
return (formatType == typeof(ICustomFormatter)) ? this : null;
}
}

Having this formatter, we can use it like this:
double width = 15.77555;
double height = 12.8497979;
Console.WriteLine(
string.Format(new DoubleFormatter(), "w={0} h={1}", width, height));

Output:
w=15.776 h=12.850
So now we have a reusable format for doubles – 3 decimal places with dot separator. That is nice, but this formatter is very simple – it formats everything (eg. DateTime) as „0:000“. This is a fast version if you know that you will only use it for formatting lots of doubles.
The real version should look like this:

public class DoubleFormatter : IFormatProvider, ICustomFormatter
{
// always use dot separator for doubles
private CultureInfo enUsCulture = CultureInfo.GetCultureInfo("en-US");

public string Format(string format, object arg, IFormatProvider formatProvider)
{
if (arg is double)
{
if (string.IsNullOrEmpty(format))
{
// by default, format doubles to 3 decimal places
return string.Format(enUsCulture, "{0:0.000}", arg);
}
else
{
// if user supplied own format use it
return ((double)arg).ToString(format, enUsCulture);
}
}
// format everything else normally
if (arg is IFormattable)
return ((IFormattable)arg).ToString(format, formatProvider);
else
return arg.ToString();
}

public object GetFormat(Type formatType)
{
return (formatType == typeof(ICustomFormatter)) ? this : null;
}
}

Example:
Console.WriteLine(string.Format(new DoubleFormatter(),
"Numbers {0} and {1:0.0}. Now a string {2}, a number {3}, date {4} and object: {5}",
1.234567, -0.57123456, "Hi!", 5, DateTime.Now, new object()));

Output:
Numbers 1.235 and -0.6. Now a string Hi!, a number 5, date 12.6.2009 17:11:35
and object: System.Object
Other examples with custom formatters can be found in MSDN.
public class AcctNumberFormat : IFormatProvider, ICustomFormatter
{
private const int ACCT_LENGTH = 12;

public object GetFormat(Type formatType)
{
if (formatType == typeof(ICustomFormatter))
return this;
else
return null;
}

public string Format(string fmt, object arg, IFormatProvider formatProvider)
{
// Provide default formatting if arg is not an Int64.
if (arg.GetType() != typeof(Int64))
try {
return HandleOtherFormats(fmt, arg);
}
catch (FormatException e) {
throw new FormatException(String.Format("The format of '{0}' is invalid.", fmt), e);
}

// Provide default formatting for unsupported format strings.
string ufmt = fmt.ToUpper(CultureInfo.InvariantCulture);
if (! (ufmt == "H" ufmt == "I"))
try {
return HandleOtherFormats(fmt, arg);
}
catch (FormatException e) {
throw new FormatException(String.Format("The format of '{0}' is invalid.", fmt), e);
}

// Convert argument to a string.
string result = arg.ToString();

// If account number is less than 12 characters, pad with leading zeroes.
if (result.Length < ACCT_LENGTH) result = result.PadLeft(ACCT_LENGTH, '0'); // If account number is more than 12 characters, truncate to 12 characters. if (result.Length > ACCT_LENGTH)
result = result.Substring(0, ACCT_LENGTH);

if (ufmt == "I") // Integer-only format.
return result;
// Add hyphens for H format specifier.
else // Hyphenated format.
return result.Substring(0, 5) + "-" + result.Substring(5, 3) + "-" + result.Substring(8);
}

private string HandleOtherFormats(string format, object arg)
{
if (arg is IFormattable)
return ((IFormattable)arg).ToString(format, CultureInfo.CurrentCulture);
else if (arg != null)
return arg.ToString();
else
return String.Empty;
}
}

using System;
using System.Globalization;

public enum DaysOfWeek { Monday=1, Tuesday=2 };

public class TestFormatting
{
public static void Main()
{
long acctNumber;
double balance;
DaysOfWeek wday;
string output;

acctNumber = 104254567890;
balance = 16.34;
wday = DaysOfWeek.Monday;

output = String.Format(new AcctNumberFormat(),
"On {2}, the balance of account {0:H} was {1:C2}.",
acctNumber, balance, wday);
Console.WriteLine(output);

wday = DaysOfWeek.Tuesday;
output = String.Format(new AcctNumberFormat(),
"On {2}, the balance of account {0:I} was {1:C2}.",
acctNumber, balance, wday);
Console.WriteLine(output);
}
}
// The example displays the following output:
// On Monday, the balance of account 10425-456-7890 was $16.34.
// On Tuesday, the balance of account 104254567890 was $16.34.



using System;
using System.Globalization;
using System.Numerics;

public class BinaryFormatter : IFormatProvider, ICustomFormatter
{
// IFormatProvider.GetFormat implementation.
public object GetFormat(Type formatType)
{
// Determine whether custom formatting object is requested.
if (formatType == typeof(ICustomFormatter))
return this;
else
return null;
}

// Format number in binary (B), octal (O), or hexadecimal (H).
public string Format(string format, object arg, IFormatProvider formatProvider)
{
// Handle format string.
int baseNumber;
// Handle null or empty format string, string with precision specifier.
string thisFmt = String.Empty;
// Extract first character of format string (precision specifiers
// are not supported).
if (! String.IsNullOrEmpty(format))
thisFmt = format.Length > 1 ? format.Substring(0, 1) : format;


// Get a byte array representing the numeric value.
byte[] bytes;
if (arg is sbyte)
{
string byteString = ((sbyte) arg).ToString("X2");
bytes = new byte[1] { Byte.Parse(byteString, System.Globalization.NumberStyles.HexNumber ) };
}
else if (arg is byte) {
bytes = new byte[1] { (byte) arg };
}
else if (arg is short) {
bytes = BitConverter.GetBytes((short) arg);
}
else if (arg is int) {
bytes = BitConverter.GetBytes((int) arg);
}
else if (arg is long) {
bytes = BitConverter.GetBytes((long) arg);
}
else if (arg is ushort) {
bytes = BitConverter.GetBytes((ushort) arg);
}
else if (arg is uint) {
bytes = BitConverter.GetBytes((uint) arg);
}
else if (arg is ulong) {
bytes = BitConverter.GetBytes((ulong) arg);
}
else if (arg is BigInteger) {
bytes = ((BigInteger) arg).ToByteArray();
}
else {
try {
return HandleOtherFormats(format, arg);
}
catch (FormatException e) {
throw new FormatException(String.Format("The format of '{0}' is invalid.", format), e);
}
}

switch (thisFmt.ToUpper())
{
// Binary formatting.
case "B":
baseNumber = 2;
break;
case "O":
baseNumber = 8;
break;
case "H":
baseNumber = 16;
break;
// Handle unsupported format strings.
default:
try {
return HandleOtherFormats(format, arg);
}
catch (FormatException e) {
throw new FormatException(String.Format("The format of '{0}' is invalid.", format), e);
}
}

// Return a formatted string.
string numericString = String.Empty;
for (int ctr = bytes.GetUpperBound(0); ctr >= bytes.GetLowerBound(0); ctr--)
{
string byteString = Convert.ToString(bytes[ctr], baseNumber);
if (baseNumber == 2)
byteString = new String('0', 8 - byteString.Length) + byteString;
else if (baseNumber == 8)
byteString = new String('0', 4 - byteString.Length) + byteString;
// Base is 16.
else
byteString = new String('0', 2 - byteString.Length) + byteString;

numericString += byteString + " ";
}
return numericString.Trim();
}

private string HandleOtherFormats(string format, object arg)
{
if (arg is IFormattable)
return ((IFormattable)arg).ToString(format, CultureInfo.CurrentCulture);
else if (arg != null)
return arg.ToString();
else
return String.Empty;
}
}

public class Example
{
public static void Main()
{
Console.WindowWidth = 100;

byte byteValue = 124;
Console.WriteLine(String.Format(new BinaryFormatter(),
"{0} (binary: {0:B}) (hex: {0:H})", byteValue));

int intValue = 23045;
Console.WriteLine(String.Format(new BinaryFormatter(),
"{0} (binary: {0:B}) (hex: {0:H})", intValue));

ulong ulngValue = 31906574882;
Console.WriteLine(String.Format(new BinaryFormatter(),
"{0}\n (binary: {0:B})\n (hex: {0:H})",
ulngValue));

BigInteger bigIntValue = BigInteger.Multiply(Int64.MaxValue, 2);
Console.WriteLine(String.Format(new BinaryFormatter(),
"{0}\n (binary: {0:B})\n (hex: {0:H})",
bigIntValue));
}
}
// The example displays the following output:
// 124 (binary: 01111100) (hex: 7c)
// 23045 (binary: 00000000 00000000 01011010 00000101) (hex: 00 00 5a 05)
// 31906574882
// (binary: 00000000 00000000 00000000 00000111 01101101 11000111 10110010 00100010)
// (hex: 00 00 00 07 6d c7 b2 22)
// 18446744073709551614
// (binary: 00000000 11111111 11111111 11111111 11111111 11111111 11111111 11111111 11111110)
// (hex: 00 ff ff ff ff ff ff ff fe)


Align String with Spaces
This example shows how to align strings with spaces. The example formats text to table and writes it to console output.
To align string to the right or to the left use static method String.Format. To align string to the left (spaces on the right) use formatting patern with comma (,) followed by a negative number of characters: String.Format(„{0,–10}“, text). To right alignment use a positive number: {0,10}.
Following example shows how to format text to the table. Values in the first and second column are aligned to the left and the third column is aligned to the right.

Console.WriteLine("-------------------------------");
Console.WriteLine("First Name Last Name Age");
Console.WriteLine("-------------------------------");
Console.WriteLine(String.Format("{0,-10} {1,-10} {2,5}", "Bill", "Gates", 51));
Console.WriteLine(String.Format("{0,-10} {1,-10} {2,5}", "Edna", "Parker", 114));
Console.WriteLine(String.Format("{0,-10} {1,-10} {2,5}", "Johnny", "Depp", 44));
Console.WriteLine("-------------------------------");

Output string:
-------------------------------
First Name Last Name Age
-------------------------------
Bill Gates 51
Edna Parker 114
Johnny Depp 44


Indent String with Spaces
This example shows how to indent strings using method for padding in C#. To repeat spacesuse method String.PadLeft. If you call „hello“.PadLeft(10) you will get the string aligned to the right: „ hello“. If you use empty string instead of the „hello“ string the result will be 10× repeated space character. This can be used to create simple Indent method.
The Indent method:

public static string Indent(int count)
{
return "".PadLeft(count);
}

Test code:
Console.WriteLine(Indent(0) + "List");
Console.WriteLine(Indent(3) + "Item 1");
Console.WriteLine(Indent(6) + "Item 1.1");
Console.WriteLine(Indent(6) + "Item 1.2");
Console.WriteLine(Indent(3) + "Item 2");
Console.WriteLine(Indent(6) + "Item 2.1");

Output string:
List
Item 1
Item 1.1
Item 1.2
Item 2
Item 2.1

Thursday, May 26, 2011

C# Regular Expressions

What is Regular Expression
Regular expressions allow for easy parsing and matching of strings to a specific pattern. Using the objects available in the RegularExpressions namespace, you can compare a string against a given pattern, replace a string pattern with another string, or retrieve only portions of a formatted string. In this example, we will construct a pattern to validate a e-mail address.

Using regular expressions to match a pattern


  1. Start Visual C#.

  2. Create a new Visual C# Console Application.

  3. Specify the using keyword on the Text.RegularExpressions namespace so that you will not be required to qualify declarations in those namespaces later in your code. The using statement must be used prior to any other declarations:
    using System.Text.RegularExpressions;

  4. Define a new regular expression that will use a pattern match to validate an e-mail address. The following regular expression is structured to accomplish three things: *Capture the substring before the @ symbol and put that into the "user" group.
    *Capture the substring after the @ symbol and put that into the "host" group.
    *Make sure that the first half of the string does not have an @ symbol.

  5. Regex emailregex = new Regex("(?[^@]+)@(?.+)");


  6. Define a new string containing a valid e-mail address. This provides a default value if the method's command-line argument is empty:
  7. String s = "johndoe@tempuri.org";


  8. Check to see if there are any command-line parameters; if there are, retrieve the first parameter and assign it to the variable "s".
  9. if ( args.Length > 0 ) {
    s = args[0];
    }


  10. Use the Match method to pass in the e-mail address variable and return a new Match object. The Match object will return regardless of whether any matches were found in the source string.
  11. Match m = emailregex.Match(s);


  12. By examining the Success property, we can decide whether to continue processing the Match object or to print an error message. If successful, display the "user" and "host" named groups within the Groups collection of the Match object.
    if ( m.Success ) {
    Console.WriteLine("User: " + m.Groups["user"].Value);
    Console.WriteLine("Host: " + m.Groups["host"].Value);
    } else {
    Console.WriteLine(s + " is not a valid email address");
    }
    Console.WriteLine();

  13. To keep the console window open after running the application, add the following lines of code:
    System.Console.WriteLine("Press Enter to Continue...");
    System.Console.ReadLine();

  14. Build your project.

To run the application in the development environment using the default e-mail address specified in the code, press F5 or select Start from the Debug menu. To start the application with a command-line argument, there are three options:
On the Project menu, click Properties, and then click Debug. In the Start Options section in the right pane, specify the e-mail address that you want to test. Press F5, or click Start on the Debug menu to run the application.


Available Regular Expression Operators


More Info:
The book Mastering Regular Expressions not only explains everything you want to know and don't want to know about regular expressions, including the regex features that are unique to .NET. It has an excellent chapter on .NET's System.Text.RegularExpressions namespace, explaining the various Regex classes far better than Microsoft's documentatio, with plenty of example VB.NET example code and some C# code showing more advanced techniques.