2. • Automatic Properties
• Extension Methods
• Object Initialization
• Anonymous Types
• Partial Methods
• Type Inference
• LINQ
• Lambda Expression
• Query Expression
• All Together
3. Language Enhancements + Query
Expressions = LINQ
Language Enhancements consists of
– Local Variable Type Inference
– Object Initialisers
– Anonymous Types
– Lambda Expressions
– Extension Methods
4. • No need of private variable
• When no extra logic is required in get and set
• private set is used for making read-only
property
• prop + double tab is code snippet
5. public class Product
{
private string name;
private decimal price;
public string Name {
get { return name; }
set { name = value; }
}
public decimal Price {
get { return price; }
set { price = value; }
}
}
6. public class Product
{ Must have both
public string Name { get; set; } get and set
public decimal Price { get; set; }
}
public class Product
{
public string Name { get; private set; }
public decimal Price { get; set; } Read only
} property
7. • Equivalent to calling the static method
• Can access only public members.
• Can add methods to other classes
◦ any methods (although look static)
◦ only from static classes
• When import a namespace that has extensions, then
added to classes
◦ once imported, called as usual
• Local methods take precedence
◦ first local for normal method, then extension
8. namespace MyStuff Extension
{ method
public static class Extensions
{
public static string Concatenate(this IEnumerable<string> strings,
string separator) {…}
}
}
Brings extensions into
using MyStuff; scope
obj.Foo(x, y)
string[] names = new string[] { "Axel", "Mia", "Niels" }; XXX.Foo(obj, x, y)
string s = names.Concatenate(", ");
IntelliSense!
9. • Can initialize fields like attribute fields
◦ new C(1, 2, name=“my class”);
◦ works if public field or if property with set
◦ can be nested (eg. Rectangle with two Points)
• Collection initializers
◦ List<int> digits = new List<int> { 0, 1};
◦ Must implement System.Generic.ICollection<T>
• Object initializers
◦ var a = new Point { X = 0, Y = 1 };
10. public class Point
{
private int x, y;
public int X { get { return x; } set { x = value; } } Field or property
public int Y { get { return y; } set { y = value; } } assignments
}
Point a = new Point { X = 0, Y = 1 };
Point a = new Point();
a.X = 0;
a.Y = 1;
11. Must implement Must have public
IEnumerable Add method
List<int> numbers = new List<int> { 1, 10, 100 };
List<int> numbers = new
List<int>();
Add can take
numbers.Add(1);
more than one
numbers.Add(10); parameter
numbers.Add(100);
Dictionary<int, string> spellings = new Dictionary<int, string> {
{ 0, "Zero" }, { 1, "One" }, { 2, "Two" }, { 3, "Three" } };
12. Type of the variable induced from expression
◦ must include initializer
◦ can’t be null. Why not?
What happens if “var” is a class in scope?
Works in foreach loops
13. • var can only be used when a local variable is declared and
initialized in the same statement; the variable cannot be initialized
to null literal, because it does not have a type – like lambda
expressions or method groups. However, it can be initialized with
an expression that happens to have the value null, as long as the
expression has a type.
• var cannot be used on fields in class scope.
• Variables declared by using var cannot be used in their own
initialization expression.
In other words, var v = v++; will result in a compile-time error.
• Multiple implicitly-typed variables cannot be initialized in the
same statement.
• If a type named var is in scope, then we will get a compile-time
error if we attempt to initialize a local variable with the var
keyword.
14. int i = 5;
string s = "Hello";
double d = 1.0;
int[] numbers = new int[] {1, 2, 3};
Dictionary<int,Order> orders = new
Dictionary<int,Order>();
var i = 5;
var s = "Hello";
var d = 1.0;
var numbers = new int[] {1, 2, 3};
var orders = new Dictionary<int,Order>();
“The type on the
right hand side”
15. • var x = new {p1 = 10, p2 = “name”};
◦ x is of anonymous type
◦ type can’t be referred to by name in program
• structural type equivalence
◦ two anonymous types can be compatible
• implicitly typed arrays
◦ var a = new[] { 1, 10, 100, 1000 };
◦ must have consistent types
◦ or have implicit conversions
16. IEnumerable<Contact> phoneListQuery =
from c in customers
where c.State == "WA"
select new Contact { Name = c.Name, Phone = c.Phone };
+
public class Contact
{
public string Name;
public string Phone;
}
17. IEnumerable< Contact > class Contact
{
public string Name;
public string Phone;
var phoneListQuery = }
from c in customers
where c.State == "WA"
select new { Name = c.Name, Phone = c.Phone };
Contact
foreach (var entry in phoneListQuery) {
Console.WriteLine(entry.Name);
Console.WriteLine(entry.Phone);
}
18. • Partial methods are methods living in partial
classes which are marked as partial
• The method must return void.
• No access modifiers or attributes are allowed.
Partial methods are implicitly private.
• Partial methods method hooks, similar to event
handlers, that developers may decide to implement
or not.
• If the developer does not supply an
implementation, the compiler removes the
signature at compile time.
19. partial class A
{
partial void OnSomethingHappened(string s);
}
// This part can be in a separate file.
partial class A
{
// Comment out this method and the program
// will still compile.
partial void OnSomethingHappened(String s)
{
Console.WriteLine("Something happened: {0}", s);
}
}
20. • Unified programming model for any data
type/source
• Collections
• Database Relational Data
• XML Files
• Extendable for anything else
• Introduce more declarative syntax
• Data is equivalent to Objects
21. C# 3.0 VB 9.0 Others…
.NET Language-Integrated Query (LINQ)
LINQ enabled ADO.NET
LINQ LINQ LINQ LINQ LINQ
To to To To to
Objects Entities SQL Dataset XML
Objects Relational Data XML
22. • Syntax based on Extension methods
• Some Extension methods may be replaced
by language keywords
– where, orderby, select, group, …
• Auxiliary language features in use
– Automatic properties
– Anonymous types
– Implicitly typed local variables
– Object initializers
23. • Working with collections
◦ Any one that implements IEnumerable<T>
• using System.Linq
24. • Generalized function syntax
◦ x.x+1
◦ in C# 3.0, have x => x + 1
• From anonymous delegate syntax:
◦ delegate(int x) { return x + 1;}
• Can have implicitly typed variables
• Can have more than one variable
• Can have expression or statement body
25. • Can be converted to delegate type
◦ if parameters and body match
◦ delegate R Func<A,R>(A arg);
Func<int,int> f1 = x => x + 1;
Func<int,double> f2 = x => x + 1;
Func<double,int> f3 = x => x + 1;
• Participate in type inference
• If expression body, get expression trees
26. public delegate bool Predicate<T>(T obj);
public class List<T>
{
public List<T> FindAll(Predicate<T> test)
{
List<T> result = new List<T>();
foreach (T item in this)
if (test(item)) result.Add(item);
return result;
}
…
}
27. public class MyClass
{
public static void Main() {
List<Customer> customers = GetCustomerList();
List<Customer> locals =
customers.FindAll(
new Predicate<Customer>(StateEqualsWA)
);
}
static bool StateEqualsWA(Customer c) {
return c.State == "WA";
}
}
28. public class MyClass
{
public static void Main() {
List<Customer> customers = GetCustomerList();
List<Customer> locals =
customers.FindAll(
delegate(Customer c) { return c.State == "WA"; }
);
}
}
29. public class MyClass
{
public static void Main() {
List<Customer> customers = GetCustomerList();
List<Customer> locals =
customers.FindAll(c => c.State == "WA");
}
}
Lambda
expression
30. • Adds querying to language
◦ important for interaction with DB
◦ but also with built-in data structures
◦ leave query planning to data structure designer
• Implemented using above functionality
◦ anonymous types and variables useful
◦ lambda expressions make it cleaner.
31. Starts with
from
Zero or more
from, join, let, wher
from id in source e, or orderby
{ from id in source |
join id in source on expr equals expr [ into id ] |
let id = expr |
where condition | Ends with select
or group by
orderby ordering, ordering, … }
select expr | group expr by key
[ into id query ]
Optional into
continuation
32. Queries translate to method invocations
◦ Where, Join, OrderBy, Select, GroupBy, …
from c in customers
where c.State == "WA"
select new { c.Name, c.Phone };
customers
.Where(c => c.State == "WA")
.Select(c => new { c.Name, c.Phone });
33. Project Select <expr>
Filter Where <expr>, Distinct
Test Any(<expr>), All(<expr>)
Join <expr> Join <expr> On <expr> Equals <expr>
Group Group By <expr>, <expr> Into <expr>, <expr>
Group Join <decl> On <expr> Equals <expr> Into <expr>
Aggregate Count(<expr>), Sum(<expr>), Min(<expr>), Max(<expr>),
Avg(<expr>)
Partition Skip [ While ] <expr>, Take [ While ] <expr>
Set Union, Intersect, Except
Order Order By <expr>, <expr> [ Ascending | Descending ]
34. var contacts = Query
expressions
from c in customers
where c.State == "WA"
select new { c.Name, c.Phone };
type inference
Lambda
expressions
var contacts =
customers
.Where(c => c.State == "WA")
.Select(c => new { c.Name, c.Phone });
Extension
methods Anonymous Object
types initializers