Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
0% found this document useful (0 votes)
13 views271 pages

C# Learning

Download as docx, pdf, or txt
Download as docx, pdf, or txt
Download as docx, pdf, or txt
You are on page 1/ 271

C#

What is C#?
C# is pronounced "C-Sharp".
 It is an object-oriented programming language created by Microsoft that runs on
the .NET Framework.
 C# has roots from the C family, and the language is close to other popular languages
like C++ and Java.
 The first version was released in year 2002. The latest version, C# 12, was released in
November 2023.
 C# is used for:

The C# programming language allows us to build many types of applications, like:

 Business applications to capture, analyse, and process data


 Mobile applications
 Desktop applications
 Dynamic web applications that can be accessed from a web browser
 Games, both 2D and 3D and VR
 Financial and scientific applications
 Cloud-based applications.
 Web Services and Web Sites.
 Database applications. etc…

Why Use C#?


 It is one of the most popular programming languages in the world
 It is easy to learn and simple to use
 It has huge community support
 C# is a simple ,type safe and powerful object-oriented language which gives a clear
structure to programs and allows code to be reused, lowering development costs
As C# is close to C, C++ and Java, it makes it easy for programmers to switch to C# or vice
versa.

what is .NET framework and how is it different from C#

 C# is a programming language.
 .Net is a framework for building applications on Windows
 .Net framework is not limited to C-sharp.
There are different languages that can target .Net framework and build applications using that
framework.
Examples are C#, F# or VB .NET.
what is Dot Net Framework?

.Net framework consists of two components.


1. CLR or Common Language Runtime and
2. Class library for building applications

History of C-Sharp.

Before C# We had two languages in the C family the C language and C++
with either of these languages when we compile our application, the compiler translates our
code into the native code for the machine on which it was running.

If we write an application in C++ on a Windows machine with 80 - 86 processor architecture


the compiler would translate our code into the native code for that machine, that is a
Windows machine with an 80 - 86 processors.

Now we know we have different hardware and we have different operating systems like
Linux. So if I took an application that compiled the application on the computer with a
different architecture that would not run. So when Microsoft was designing the C-sharp
language on the .NET framework they came up with an idea, that they borrowed from the
Java community.

In Java the computer code is not translated directly into the machine code.
It's translated into an intermediate language called bytecode

and we have the exact same concept in C-sharp.


So when we compile our C-Sharp code the result is what we call IL or intermediate language
code and is independent of the computer on which it's running.
Now we need something that would translate that IL code into the native code or the machine
that is running the application. And that is the job of CLR our Common Language Runtime

So CLR it is essentially an application that is sitting in the memory whose job is to translate
the IL code into the machine code. And this process is called just in time compilation or JIT.
So with this architecture we can write an application in C-sharp and we don't have to worry
about compiling that into the native code for different machines. As long as a machine has
CLR that can run wer application.

Architecture of .NET Applications:

.NET Architecture:

When we build an application with C-Sharp our application consists of building blocks called
classes
.
These classes collaborate with each other at runtime. And as a result the application provides
some functionality.
.

what is a class?

A class is a container that has some data which is also called attributes and functions which is
also called methods.

Function or methods have behaviour.


They execute code.
They do things for us

Data represents the state of the application.

Think of a car a car has some attributes like its model its colour.
These are the attributes of a car.

The car also has some functions.


We can start it or we can move it so we can think of a car as a class
in a real world application.
We have tens hundreds or even thousands of classes each class responsible for a piece of
functionality.

An example of that is classes that are responsible for getting the data from the user process
the data and display something to the user.

Now as the number of classes in an application grows we need a way to organize these
classes.
That’s where we use a namespace.
So, a namespace is a container for related classes.
For example, in .NET framework we have name spaces each containing tens of related
classes.
We have name spaces for working with data like databases.
We also have name spaces for working with graphics and images.
We have name spaces for working with security

now in real world application as these name spaces grow, we need a different way of
partitioning an application and that’s where we use an assembly

An assembly is a container for related name spaces.


Physically it’s a file on the disk which can either be an executable or a DLL which stands for
dynamically linked library.
So when we compile an application the compiler builds one or more assemblies depending on
how we partition wer code in the next picture.
Classes  Namespace Assembly Application.

visual studio filenew projectOK


and this dialog on the left side we've got a section called templates and here we see the kind
of applications we can build with C-sharp.

So as we see in the list we can build desktop applications web applications apps for cloud,
services workflows and various kind of things.

But in this course we're just going to focus on console applications


A console application is a very simple application that does not have a graphical user
interface and it's a great learning tool for learning a new language.

So on the left side select Windows and on the right side select console application then give a
name to the project.

So let's call it hello world which is a common tradition when learning a new language and
specify a location.

We can put it wherever we want.

I know this concept of solution in visual studio we have this concept of solution which can
have one or more projects with a very simple application.
We have only one solution and one project but as wer application grows we add more
projects each responsible for something different.
No we don't have to worry about it now click OK.

All we need is the code editor here

and sometimes we need the solution explorer.

In fact, I personally hardly ever use solution explorer because I do everything with my
keyboard. And if we watch my course double wer coding speed we will see that everything is
possible with keyboard.

Now let's take a look at this first our program so we created a console application and on the
right side we see the solution explorer panel in case we don't see that go to view and select
solution explorer.
So at the top we see we have a solution which has only one project under that we've got the
project called Hello world.
Look at this four items here.
Properties expand that we have a file here called assembly info.

This is the identification for the assembly that will be produced as a result of compiling this
application.

So when we compile a console application we're going to get an executable. And that's an
assembly that assembly has an identification.
Look at these attributes here.
Like the title, description which is currently not set.
Company, product, copyright, trademark, culture a great we know various kind of things like
even version.

So these are all part of assembly identification or assembly manifest. In most cases we don't
have to worry about it, but if we want to create an assembly and we want to distribute it Send
to other people.

Then we may want to come here and give it a proper name and a proper version.

So for now we don't have to worry about it.

Under references We see any assemblies that this project is referencing to do its job.
When we create a project with visual studio by default it set a reference to a bunch of
assemblies that we see here, these are all part of Dot Net framework.

So at a minimum Visual Studio assumes we're going to use classes in System assembly or
System.Data to work with databases and so on.
We may not necessarily use all these assemblers in wer project but that's just part of the
template.

App.config is an XML where we store the conflagration for this application.


Sometimes we may want to store connection strings through the database or we may want to
have some settings about wer application. All of them will end up here. And finally we see
program the C-s which is where we're going to start writing code.

So in this file program.cs on the top we see a bunch of using statements.

What is this all about. Well our project is called the hello world. So by default visual studio
creates a namespace called HelloWorld when we write code in this namespace, we have
access to any classes defined in this namespace.
So if we want to use a class that is defined in a different namespace we need to import it in
our code file. And that's why we use the using statement.

So by default Visual Studio adds this five using statements.


System is a namespace in .Net Framework and that's where we have all these basic utility
classes and primitive types typewriter
System that collections that generic is used to work with lists collections and so on system
that link is used to work with data.
And it's a comprehensive topic that I have covered in my C-Sharp And of course system the
text is used to work with text and coding and stuff like that.
And finally system the threading is used to build multithreaded applications in this video
we're going to create a very simple application and we're not going to use any of these four
name spaces here so we're just going to use system for now.
I leave them there and then I'll show we how to clean them up.
All right so here's our namespace and inside them space.

By default, we have a class called program so every console application we create with
Visual Studio has a class called program Inside program by default.

We have a method or a function called Main and that's the entry point to the application.
So when we run wer application C-L or executes the code inside main method and that's
where everything
kicks off this method is declared as static.
And that's something I'm going to cover later in the next section.
Methods have input and output.
So what goes inside parentheses the input to the method which we call parameter or
argument.
Know that parameters are optional.
But in this case the default template the main method has a parameter called args which is of
type String
Array.
We're going to learn about String Array in the next section.
What do we see before the method name is the return type or the output of the method void in
C Sharp
means nothing.
That means this method does not return any value.
It just contains some code that's it.
Also note that C sharp is a case sensitive language so this main has to be with capital M
otherwise
C-L R is not going to find this method as the entry point of the application.
Okay and one last thing is not this curly braces so we're half a block of code.
We need to surround it with curly braces so that is applicable for methods for classes and for
name
spaces.
Right now most write a very simple program.
So let's go here.
We have a class called Konsole which is used to read data from console or write data to it.
It has a bunch of methods we can access this Smethurst using the dot notation.
And here we see various members of this class.
Methods are indicated by a purple cube.So beep is used to play a beep sound.All clear is used
to clear the console.
We get to use the right line method.This method can optionally take a parameter.So I'm going
to pass a string here.

Hello world.

Just that I know that statements in C# terminate with a semicolon as we see here.
Now take a look at using system on the top.
Do we see that it's highlighted where as the others are greyed out.
The reason for that is in this file we are using a class called Konsole which is defined in the
system
namespace.
That's why that using statement is active.
We are not using any classes defined in other names spaces and that's why they're great out so
we can
get rid of them to make our code cleaner.
We can delete each one by control X like that.
Or if we're using resharpen we can't get rid of all of them by pressing alt and enter here and
selecting
the first option which is remove unused directives in file so it's faster.
Now let's run the application with control and F5.
So this we know that we see here this black window is what we call console and that's why
this kind
of project is called console application.

Summary:
C# vs .NET

C# is a programming language, while .NET is a framework. It consists of a run-time


environment (CLR) and a class library that we use for building applications.

CLR

When we compile an application, C# compiler compiles wer code to IL (Intermediate


Language) code. IL code is platform agnostics, which makes it possible to a take a C#
program on a different computer with different hardware architecture and operating system
and run it. For this to happen, we need CLR. When we run a C# application, CLR compiles
the IL code into the native machine code for the computer on which it is running. This
process is called Just-in-time Compilation (JIT).

Architecture of .NET Applications

In terms of architecture, an application written with C# consists of building blocks called


classes. A class is a container for data (attributes) and methods (functions). Attributes
represent the state of the application. Methods include code. They have logic. That's where
we implement our algorithms and write code.

A namespace is a container for related classes. So as our application grows in size, we may
want to group the related classes into various namespaces for better maintainability.

As the number of classes and namespaces even grow further, we may want to physically
separate related namespaces into separate assemblies. An assembly is a file (DLL or EXE)
that contains one or more namespaces and classes. An EXE file represents a program that can
be executed. A DLL is a file that includes code that can be re-used across different programs.
In the next section, we'll learn about basics of the C# language, including variables,
constants, type conversion and operators.

========================================================================

variables and constants.

A variable is a name that we give to a storage location in memory where we can store a value
and it can stand in any immutable value that is a value that we know at compile time and that
value cannot change throughout the life of the application.

Why do we use constants?

The reason for that is to create safety in our application.


Imagine we're creating an application that involves some mathematical computation around
circles.
We have this number called P which is three point 1 4 and we use that to calculate the area of
a circle.

That number should always be the same.


We don't want to accidentally change that in our program.
If we accidentally change that everything is going to blow up in terms of the results the
program produces.

So we declare that number as a constant.


And this way we create safety in our application in C-sharp to declare a variable.
We start with a type followed by an identifier and finally semicolon here and represent
integer which
is a number between minus 2 billion and plus 2 billion later in this video we show we all the
primitive
types that we need to know.
Also not that C-Sharp is a case sensitive language which means in this case these two
identifiers are
different.
One has Laura case and one has uppercase and when declaring a variable we can optionally
assign it to
value like what we see here.
We don't have to but there is one thing we need to know about variables and that is we cannot
use
a variable unless we initialize it.
So let's say if I declared this number here and I decide to displayed on the console my
application
will not become part.
I have to assign it a value before I can use it before I can read it.
I will show we that later when we jump to coding to declare Konstam we start with the key
word Konst
.
Next we have the data type and an identifier.
And here we have to initialize it with some value.
We cannot define a constant without setting its value.
There are a few things we need to know about identifiers.
First one is that an identifier cannot start with a number.
So we cannot have an identifier like the one we see here.
Instead we need to replace one with the word one.
Also an identifier cannot include whitespace so we cannot have an identifier like first space
name
.
It has to be one word and identifier cannot be a reserve keyword like in that we saw earlier.
If we're desperate to use a word that coincidentally clashes with one of the C-sharp keywords
we can
Perfect's that with the at sign.
And finally as a recommendation always use meaningful names.
For example avoid a name like F and instead use first name.
This way wer code will be more readable more maintainable and cleaner and everybody will
understand
that in terms of naming convention.
Here are three popular naming conventions that have been around in the C language family.
We've got camel case Pasko case and Hungarian notation with camel case as we see I have
bolded here
.
The first letter of the first word is Laura case and the first letter of every word after it has to
be upper case with Pasko case the first letter of every word has to be all uppercase with
Hungarian
Notation prefixed the name of a variable with the data type it uses.
So here SDR represents a string.
Angelia notation is not used in C Sharp and I have noticed programmers coming from C or
C++ might ground
use that in their code.
If we're one of them I highly recommend we not to use Hungarian notation because C-Sharp
developers
are not used to that and they don't like to see Hungarian notation in the code.
It makes wer code look a little bit ugly.
So in C-sharp to name wer local variables.
Use camel case.
So as we see here the first letter of the first word is lowercase and if we had more words here
in
the identifier the first letter of every word had to be uppercase for constants use Pascal case.
So here we see I've got a constant here constant integer and the first letter of every word is
uppercase
.
Here is the list of most commonly used primitive types in C-sharp.
In fact the actual list is slightly bigger than this but I deliberately decided not to include those
data types because they're hardly ever used.
In fact they are there for interoperability with other languages.
I personally over the past 12 years off me coding in C-sharp.
I've hardly ever used them.
In fact never.
So I decided not to confuse we with too much details that we don't need in the next slide.
I've got a link here in case we want to learn about the other primitive types.
So let's take a look at the table here.
On the flip side I have divided this data types into four categories.
Integral numbers real numbers character and boolean.
This column shows the C-sharp data types and these are C-Sharp keywords.
Note that the Shoki words are always lower.
Each of these C-Sharp keywords or C-Sharp types maps to a type in dot net framework which
is displayed
in this column so these types are part of the dot net framework.
And when we compile wer application the compiler internally would translate the C-sharp
keyword we
use wer to equivalent of that type.
The third column here shows the number of bytes each data type uses.
I have listed the data types from the smallest to the largest in each category.
So in the category of integral number as we see byte is the smallest.
It takes only one byte as long as the largest and it takes eight bytes the more bytes we have
the more
storage we have.
And we can store in larger numbers.
We don't really have to memorize the range of each data type but remember byte can store a
value between
0 to 255.
Short can store a value between minus thirty two thousand two plus thirty two thousand
integer can store
a value of between minus two billion two plus two billion and long is even bigger than that in
terms
of real numbers.
We have three data types.
Float double and decimal float maps to the single type in that framework and it takes four
bytes.
And as we see it can store a very large number.
Double is twice as big so it uses 8 bytes and decimal uses 16 bytes.
The more precision we need the bigger data type we use.
We also have character which is represented by Charke keyword and it's two bytes.
So characters in C-sharp are Unicode.
And finally we have bool which represents boolean which can be either true or false.
In case we want to learn more about the other data types that I told we they're not really used.
We can simply go to Google and search for C-Sharp built in types and the first page is the
MSDE and
page that lists all the primitive types in SUCIA.
Most of these data types are pretty straight forward but there is something tricky about real
numbers
in this table.
I have listed the data types we have for real numbers.
Load double and decimal.
I've highlighted double because that's the default data type used by C-Sharp compiler.
When we're using real numbers.
So if we want to declare a float we need to explicitly tell the compiler to treat the number we
have
as a float.
Here is an example.
I've declared a float.
Call it number assign it one point to.
Here I have either the suffix f and that is to tell the compiler to treat this number as a float.
If I didn't have this F here compiler would think 1.2 is a double because double is the default
data
type for real numbers.
And of course I cannot assign a double number into a float so the program would not comply.
Same applies to decimals.
So if we want to declare a decimal we need to add the suffix M at the end of the number in
the jar
.
We also have a few other types which are not considered primitive types and there are string
array ino
and class.

concept of overflowing.

We have declared a variable of type byte code number and assign it to 255.
As I told we earlier in the slide 255 is the largest value we can store in a byte.
Now in the next line I'm increasing the value of number by 1 and trying to store 256 in the
number.
But if we compile the application and display number on the console we'll see 0.
And this is what we call overflowing.
So we have exceeded the boundary of the byte data type in C-sharp by default.
We don't have overflow checking which means we can modify the value of a viable add
runtime and if we
go beyond the boundary of it's underlying data type we will get overflow.
Now sometimes this is not desirable in wer application.
We want to stop water flowing.
If that's the case we need to use the check Keyworth.
So here is how it works.
We have to check key word followed by curly braces which indicate the code block and
inside that block
we have the variable declaration and any kind of Earth mining operations with this code
overflow will
not happen at runtime.
Instead an exception will be thrown and the program will crash unless we handle the
exception.
The topic of exceptions is an advanced topic and I've covered it in my C# advanced course.
For now all I want we to know is that if we use the check keyword overflow a lot happen and
instead
the program will throw an exception.
Now do we really need that in reality.
Honestly I have never ever ever came across this situation.
Because if I was concerned that in this case my number variable would overflow.
I would just simply use the short data type instead of byte but I decided to include the concept
of
overflowing because I wanted my C Sharp course to be comprehensive So just be aware of
that.
In case we hear about overflowing summer but we're probably not going to use that in the
real world
in the next lecture we're going to talk about the concept of scope

scope:

what is the scope?

scope is where a viable or a constant has meaning and is accessible.


Take a look at this block of code here.As we know a block is indicated by curly braces.Here
we have three blocks of code.Here's one here's another and here's the last one in the first
block.I've got a variable called A and A is accessible anywhere inside this block or any of its
child blocks.

If I go out of this block and try to access a the program will not compile the same rule applies
to
other variables.
So let's take a look at this block here.
B is meaningful anywhere inside this block or any of his children.
If I go outside this block and try to access B I'm going to get a compile time error.

OK let's start by declaring a variable of type byte and call it number.


Now we want to display it on the console.
So as we remember from The Last Lecture we type console Daut writes line unput the
variable here.
Note that as I was typing console dot WriteLine my resharper plug in are magically added
this using
statement on the top system is a namespace and Console is a class that is defined in the
System namespace.

So in order to use the console class we need that declaration here on the top.
If we're not using resharpen we have to go here and manually type using System semicolon.
OK now take a look at this number here.
It has a red underline.
And if we put the mouse cursor here it says local variable number might not be initialized
before accessing
.
If we remember from the slides I told we in C-sharp before we can access a variable we need
to set
it in it to initialize it.
And that's the reason here we have the red underline we cannot display the number on the
console before
initializing that.
So if I try to compile the application we're going to get an error to compile an application we
press
control shift and B.
And here's the aerialist use of unassigned local variable number.
We can solve this problem by initialising number like setting it to 2 for example.
And we see the red underline is gone.
We can compile again.
Control shift B will succeed.
Take a look here.
OK.
Now we can run the application by press and control and F 5.
OK.
So we got two on the console.
Now let us extend this example and declare a few more variables can define an integer int
count equals 10 and a float float.
So a total price equals twenty ninety five dollars.
Now note this red underline here.
Let's find out what's happening here.
So I put the mouse cursor here.
It says cannot convert.
Source type double to target type float.
If we remember from the slides I told we by default the seashore compiler traits real numbers
like
this one here as double where as we are declaring a float.
So here we need to explicitly tell the compiler to treat this real number as a float and we can
do that
by appending an F at the end.
So the error is gone.
Mystic inner character char character A calls a.
No that is are we enclose characters by a single quote like here.
We can also declare a string string is not one of the primitive types and I have covered it in a
separate
lecture in this course.
But for now let me show we how to declare a string which just type string.
Give it a name first name a cause Marsh know that with strings being close them in double
code.
So that's one of the differences between strings and characters.
And finally let's declare a bull.
Bull is working a course.
True.
So with boules we can either set them to True or false both true and false are Keyworth as we
can see
they're indicated by the blue color here and they're lowercase.
So everything we see here that is blue is a keyword like a static void string class namespace
and all
these data types here nounless display these variables on the console.
So let me show we a trick.
Instead of writing cancel the write line.
We can do a shortcut.
This is what we call a code snippet.
So we type the CW that is short for console right line and then press tab and visual studio
automatically
converts that to cancel the right line.
There are various code snippets that help we write code faster and I will try to point them out
throughout
this course.
So let's just play count.
Now another one.
Total price.
Not that I can't just type T.L. And here's what we call intellisense is Visual Studio.
Auto completion mechanism.
We don't have to type the full name of a type or a variable as long as the intellisense detects
that
and is highlighted here like total price.
We can simply press tab and there we go.
Visual studio automatically completes that for us.
Let's display the character.
Same here.
I just press tab again.
I typed only a few characters that can press tab or enter.
And finally is working.
We run the application by control at 5.
So we got all these values on the console
OK now let me show we something else in C-sharp.
We have a keyword called vore which makes variable declarations easier.
For example here instead of explicitly specifying the data type for each of these here I can
simply
type var and I let the C-sharp compiler detect that data type for this variable here.
So let me replace all of this with var.
OK now if we hover the mouse over the word key word we can see the underlying data type.
And in this case it is system that boolean which is the dominant type which maps to C-Sharp
bool keyword
.
I with this one that's a string.
And this one is a character and this one is system that single which maps to float in.
And in the case of count it's in 32 which is integer and same for number.
So the tricky thing here is by default C-Sharp creates integral numbers as integer.
And when we use the VAR key word it assumes that it's an integer.
If we really want to go for a byte then we have to explicitly say mystified as byte here but tell
we from experience it's safe to use integer.
In most cases in fact if we look at the classes in the .NET framework in most cases integer is
the data type used for representing integral numbers.

OK I reverted back.
So it's a char which is a character we can put the mouse cursor here and press control and
then click that opens the object browser window.
Take a look here is Object Browser and it's a way to look at the various classes in wer project
or in the top that framework.
In this case because I did a control click on the char or var keyword.
This is what we got here.
So char is highlighted in the ogic browser on the right side we see all the members of the char
type
.
So these purple ones are functions or methods.
If we scroll down here we'll see two fields here main Valeo and max value.
We'll explore them shortly and note that here is the declaration of char char is a structure we
will
cover as structures later in this course.
And note that it's a member of System namespace.
We can click system and that shows the System namespace as well as all the types defined in
the System
namespace.
So these are part of the dominant framework.
OK let's close this for now.
Let's explore another example.
So I'm going to get rid of all the code here we because simply press control X on each line
and that deletes all these lines here.
OK let's do it.
Cancel the write line.
So CW tab this time I pass a string here and we specify two placeholders
and finally supply a couple of arguments.
OK let's see what's going on here.
So here what we have is called a format string.
It's a kind of string that can be used as some kind of template.
So at runtime what we have here indicated by curly braces and zero as the argument will be
replaced
by the value we pass here.
So 0 represents the first argument after this format string and one represents the second
argument after
this format string in this case byte the next value.
So let's run this application.
We got 0 and 255 and that's the range that we can store in a byte.
We can do the same with the float.
So CW tap a format string
float mean value float max value.
Run the application.
So this is the range we can store with a float.
It's a huge number that is displayed using the scientific notation
.
OK now let's take a look at constants.
So I get rid of these two lines here.
Control X control X we define a constant with the const keyword Konst float P three point 1
4 and we
have to put f at the end because it's a float.
Now because we declared p as a constant here I can change it in my program so I can go here
and say
P it cools one.
The compiler is not happy and that's why we see that red underline here.
If we hover the mouse here it says read only local content cannot be used as an assignment
target.
It's a little weird expression to understand but basically the intention of using constants is to
have
some kind of safety in wer program.
So if there are values that should not be changed beyond wer program we defined them as
constants
.
And this way we won't accidentally modify their values

And this video I'm going to talk about various kinds of type conversion in Souchong we have
implicit
type conversion explicit type conversion which is also called casting and we also have
conversion between
non-compatible types.
Here is an example of implicit type conversion.
A bite as we know takes only one bite of memory and an integer takes four bytes.
So we can easily copy a byte to an integer.
What happens at runtime is let's take a look at this slide.
So here is the binary representation of our b variable here.
So one is represented as seven bits of 0 and 1 bit of one.
When we copy a by to an integer what the runtime does is it prefixes that value with a bunch
of zeros
to fill the four bytes.
So there is no data loss.
In situations like that when the compiler is 100 percent sure that the types are compatible and
no data
loss will happen.
Values can be converted to a different type implicitly.
Here's another example of implicit type conversion.
So we have an integer set to 1 and we copy that to a float.
Again in this example no data loss will happen.
Well let's take a look at this one.
Here we have declared an integer and we are trying to copy that to a byte and integer is four
bytes
.
So when we convert that to a byte three bytes out of four bytes will be gone and there is a
chance for
data loss.
Now data lost doesn't always happen.
It only happens if the value will be stored in the integer is beyond the capacity of a byte.
In this example one can be stored in a byte so no data loss will happen.
But if we had let's say 300 here we cannot store 300 in a byte.
So as a result of that conversion they told we lost when the compiler knows that there is a
chance for
data loss.
It doesn't allow implicit type conversion and we need to explicitly tell the compiler that we're
aware
of the data loss and we still want to go ahead with the conversion.
In situations like that what we do is we prefix that variable with the target type.
So here I'm trying to convert I to a byte.
This is what we call as casting.
Here's another example.
So we have a float set to 1.0.
And if we try to convert that to an integer the compiler would complain.
I was sure that later in the coding demo.
So we need to tell the compiler that we are aware of the data loss and we still want to convert
F which
is a float to an integer.
So we cast it like here.
Sometimes we are working with types that are not compatible but we still need to convert
them.
For example we might have a number represented as a string as we see here and we need to
convert it
to an integer.
In situations like that because string and end are not compatible we cannot use explicit
casting.
So we need a different mechanism for converting a string to a number.
In situations like that we need to use the convert class or use the Parse method to convert
classes
part of data framework and it's defined in the system namespace.
It has a bunch of methods for converting various types to other types and they all start with
two.
In this case we're trying to convert as much as a string to an int 32 and 32.
As we know is a dot Net Framework type which maps to a C-sharp integer type.
Remember a byte is one byte as short is two bytes and integer is four byte long is eight bytes.
We probably know that each byte has eight bits.
So an integer which has 4 bytes times eight beats ends up being 32 bits.
That's why it's called two in 32 and in 16 which represents 16 bits equals two short which is
two bytes
.
We also have this parse method here all the primitive types that I explained in the last lecture
like
integer long float boolean.
They all have this parse method and the Parse method takes a string and tries to convert that
to the
target type.
In this case an integer.
Here are some of the methods that we can find in the convert class to byte which converts the
given
value to a byte to in 16 to convert the given value to a short to in 32 to convert the given
value to
an integer and 2 in 64 to convert the given value too long.
OK enough theory.
Let's jump into code and see all this concept in action.
Okay let's say implicit type conversion in action first I declare a byte.
Call it B.
Answer that one.
And I declare an integer and set it to be.
Again to recap a byte is only one byte and an integer is four bytes.
So we can copy me to I without data loss and as we see there is no compile time error here.
Let's put the eye on the console so cancel that right line and we pass on here.
Note that as I typed console the right line.
My resharpen plug in automatically.
I did this using System statement on the top again.
If we don't have the sharper We need to go manually add this statement here we run the
application
by control on F5.
So we got on the console.
Now let's reverse this and see what happens.
So I'm going to get rid of this code here.
Control X control X control x.
First I declare an integer.
Set it to 1 then declare a byte and try to copy I to be.
We immediately got this red underline here.
If we hover the mouse here that tooltip says cannot convert source type into the target type
bytes
.
Sometimes this error might be in a different file which is not open in visual studio here.
So we may see the error when compiling the application.
Let's simulate that.
So I compile this application by Control shift and B which stands for build.
So here is the error cannot implicitly convert type into two byte an explicit conversion exists.
Are we missing a cast.
So now we understand the concept of implicit versus explicit type conversion.
So what we need to do here is to do a cast.
So we cast an integer to a bite.
In this case no data loss will happen because the value is small enough to be stored in one
byte.
Let's put me on the console console the right line be run the application.
So everything is good.
But let's see what happens if we said I to let's say thousand we cannot store the number of
thousand
in a byte.
The maximum we can store in a byte is 255.
So if we run the application now we got to 32 because some of the bits were lost and this is
the reason
that C-Sharp compiler knows that there is a chance for data loss and it forces we to explicitly
specify
the cast.
Sometimes we know that despite the differences in data types there is no chance of data loss
like in
the last example where I was set to 1.
In those cases we can safely apply a cast.
OK let's take a look at non-compatible types.
So let's clean up this code.
I start by declaring a string is called a number and set it to 1 2 3 4.
Just recapping from The Last Lecture note that here I could declare these with the very key
words and
C# compiler automatically detects that this is a string.
So a number will be defined as a string.
And we can see that by hovering the mouse here it says system that string.
Now let's say we want to convert that to a number.
If I declare an integer like I I cannot cast that number to an integer because they're not
compatible
.
Let's take a look at the error cannot cast expression of type string to type int.
So if we see that error that's the time when we need to use the converse class.
So we type in convert dot.
Take a look at this method to here to bite to char to in 16 in 32 and many other methods here.
So let's convert that to an integer which is 32 and past number as an argument here.
Now let's print out the eye on the con.
.
Run the application.
So it is one two three four.
All good.
But let's see what happens if instead I declared this as a byte.
And here we need to use convert dot to bite.
And here with display being on the console a byte does not have enough storage to store the
value of
1234.
So when we run the application now
application crashed we can sell this here.
And here's the exception exception is Dartmouth's frameworks error reporting mechanism.
It's an advanced topic and have covered it in detail in my C-Sharp advanced course.
But in this video I will briefly show we how to handle exceptions.
So here it says unhandled exception the type of exception is system the overflow exception
which means
we try to store a value that goes too large or too small for a byte.
So each exception or error as a type in this case the overflow exception and has a message
value was
either too large or too small for an unsigned byte.
Sometimes the exception messages are friendly enough that are easy to understand.
Sometimes they're a little bit tricky.
And the best way to work out what is going wrong is to jump on Google and search for the
error.
And there's pretty much always a stack overflow page that explains that.
Now let's discard that.
Let's see how to handle the exception here.
So the exception happened during conversion of that string to bite what we need to do here is
to wrap
these few statements with a try catch block.
Let's see how it works.
So I just typed try and press the enter and visual studio automatically generated this block for
me
.
Again this is what we call a code snippet.
Let me do this I show we one more time.
So try a serious try here and they Intellisense and this icon represents a code snippet.
So if I press enter or tab we automatically get this code block.
So what I'm going to do now is to move this code into a try block and the catch block gets an
exception
by default visual studio as this throw here.
Don't worry about it just delete it again.
I will explain it in detail in my C-Sharp advanced course.
For now let's see what's going on here.
So the code that we put inside the try block will be somehow monitored and if an exception
happens
this block will be executed.
This prevents wer application from crashing.
The reason our application crashed earlier was because we did not handle the exception.
So if we don't handle exception the exception will be propagated to the Dartmouth runtime
and the runtime
mechanism is to stop wer application and display the error.
Here we can handle the exception and that would prevent exception from being propagated to
the runtime
.
So instead we can display a friendly message to the user saying for example console that right
line
.
The number could not be converted to a byte.
Now let's run the application again.
See we got that friendly message and application didn't crash.
So what I want we to take away from this lecture is this Convery class.
Works pretty well in most cases but in cases where the source type cannot be converted to the
target
type there is a chance for exception.
And we need to be aware of that and what we need to do is to wrap this block of code with
try catch
.
Let's take a look at one more example before we finish this lecture.
Let's remove this and instead define a string.
Call it as we are and set it to true.
We can use the converse class to convert that value to a boolean so it will be a Cool's convert
that
to boolean.
And we passed that SDR.
Here again in this example the string and bool are not compatible and that's why we cannot
use explicit
casting.
So here we are using the converse class.
Can display be on the console.
Let's run the application.
So the truth string was successfully converted to a boolean value.
OK that's pretty much it for this lecture.
Before I finish I just need to emphasize something here that throughout this course during
early lectures
we may see me using some short variable names like B or SD are here.
That's purely for demonstration and keeping things simple and in building real world
applications.
We should really avoid naming our variables a b c SDR.
It's not really a good practice.
The only exception is when we get two loops which we will see later in this course in four
loops.
We use counter variables and we call them I or J.
It's a common convention.
Now here we are just starting to learn C-Sharp and it's really impossible for me to
demonstrate building
a real world application because we're just covering the basics or alphabets.
I hope we enjoyed this lecture and thank we for watching

OK we go to operators and C-Sharp we have five types of operators arithmetic comparison


assignment logical
and bitwise.
Let's take a closer look at each of these operators.
We use arithmetic operators in computations where we are working with numbers.
So as we see in the slide we have add subtract multiply divide and remainder of division.
We also have 2 arithmetic operators called increment and decrement which are shortcuts or
adding one
or subtracting one from a variable.
So A-plus plus is equivalent to a equals a plus one.
Now with this increment and decrement operator there are two ways we can apply them.
We can use them as a postfix.
So in this example a use one.
And when we apply the postfix increment operator first the value of a is assigned to be so so
is going
to be 1 and then 8 is incremented by 1.
So in this example after the second line is execute it is going to be 2 and B is going to be 1.
Now let's take a look at a different way of applying increment operator as a prefix.
So in this example and the second line first is incremented by 1 and then it's assigned to be.
So after the second line both A and B are going to be 2.
So be aware of this difference.
OK next comparison operators.
So we got equal which is indicated by double equal sign not equal greater than greater than or
equal
to less than and less than or equal to.
Now what I want we to pay attention to in this list is that the testing for equality is
accomplished
by double equal sign.
And that's different from a single equal which is the assignment operator next assignment
operators
.
So the most commonly used is the one with a single equal sign.
So here we said eight to one.
Pretty basic.
Now look at the next four types of assignment operators addition assignment subtraction
assignment multiplication
assignment and division assignment.
Let's see how they work.
For example addition assignment a plus equal three means add three to eight.
So it's equivalent to writing a equals a plus three and the same rule applies to other for
assignment
operators logical operators are used in Boolean expressions which are often used in
conditional statements
will get to conditional statements later in this course.
So a real world example is where we have a condition and we want to make sure that
condition and another
condition both are true.
Or maybe one of them is true.
So that's where we use a logical operator in C Sharp the logical and is indicated by double
ampersand
and the logical or is implemented by double vertical line.
We also have the not operator which is indicated by an exclamation mark.
And finally here we've got the bitwise operators bitwise operators are often used in low level
programming
like when working with Windows API or in sockets or encryption explanation of these is
beyond the scope
of this course.
But if we're interested let me know and I write a blog post for we.
Now what I want we to take away here is that the bitwise and is indicated by a single
ampersand whereas
the logical end which we use in conditional statements is indicated by double ampersand.
Same for bitwise OR.
And logical or.
So remember the difference.
OK in theory let's flip over to Visual Studio and see all these concepts in action

OK let's start with the Earth mining operators first.


So I defined two variables a cost ten because three let's add them together and display the
results
in the con..
That's pretty easy right.
Run the application.
So the result is 13.
Now let's take a look at division.
So I replaced the ADD operator weight division.
The result is three.
The interesting thing here is because both a and b are integers the result of the division ends
up being
an integer if we like a floating point number as the result of the division.
We need to cast both these numbers to a float.
So
like this knife we're on the application.
The result is a floating point number.
Now let's look at the more tricky example.
Let's say see is three B's two and A's 1.
I want to show we the concept of operator precedence.
So if I type A plus B times c..
What do we expect the result to be from a mathematical perspective.
B should be multiplied by C first.
Which means two times three equals six.
And then it should be added to 1.
So the result should be 7.
Let's run the application.
So C-Sharp behaves exactly as what we expected.
So multiply or division operators have higher precedence than add or subtract if we like to
change
the precedence.
We can do so by using parenthesis.
So in this case if we would like to have a and b added together first and then multiplied by C.
This is how we would achieve that.
In this case the result would be 9.
There we go.
OK.
Now let's take a look at comparison operators.
So let's get rid of C here and instead see if a is greater than B.
Very simple example right.
The result is false.
So what I want we to know here is the result of the comparison expression is always a
boolean value
which is true or false.
We can't test for equality.
So double equal sign.
In this case a is not equal to be.
So the result should be false
.
Now let's see the not equal operator.
So simply have an exclamation mark here followed by an equal sign.
In this case because A is not equal to be the result should be true.
OK now let me show we a more tricky example
.
What do we expect here.
Well first this is the NOT operator which is applied on Boolean values or boolean
expressions.
In this case this is a boolean expression.
And as we saw earlier it was true because A is not equal to be.
So we played the NOT operator to that.
And the result ends up being false.
Let's run the application.
So we got false here but this code is not easy to understand or easy to read because here we
have two
negatives one negative and two negative.
And for us humans to be negative is hard to comprehend.
Two negatives always equal to 1 positive.
So in wer program if we end up in situations where we have two negatives make sure to
always inverse
them with one positive.
So in that case I can get rid of the first negative and convert the second negative to a positive
like
that.
And we will get the same result which is false.
Now let's take a look at logical operators.
So I create another variable here.
VRC because thery want to change that to see greater than B and C greater than 8.
What do we expect here as the result.
Well C is greater than B.
So the result of that expression is true.
Also C is greater than a.
So the result of that expression is true as well.
And here we have the and operator so true and true equals to true.
Let's run the application.
There we go.
Now let's make a tiny change here.
So this time because we know C is not equal to a this expression evaluates to false true and
false results
in false.
Let's run the application.
So we got false.
Now let's see the effect of the OR operator.
So I got to replace that and with or.
Which is double vertical line.
In this case that is true or false.
The result ends up being true.
And of course we can apply and not operator here.
As we saw earlier
which changes to true to false.
Now this expression doesn't really look easy to understand.
It's just purely for demonstration of how we can combine different operators and make up
more complicated
expressions.
OK that's it for this lecture.
I hope we enjoyed it.
And thank we for watching
OK so we got to comment.
A comment is text that we put in our code to improve its readability and maintainability in C-
sharp
we have two ways to write comments.
If a comment is only a single line we can prefix a comment with double slash.
But if wer comment is longer and it's multiple lines we need to started with Slash start and
then
finish it with Star slash.
This type of comment is more like the comments we used to write in C and C++ code.
These days it's more conventional to write either a single line or multi-line comments
prefixing word
double slash.
So in this example we can rewrite this multiline comment with double slash style like this.
Now as a rule of thumb keep wer comments to minimum use comments only when required
and that's when
explaining whys hows constraint and things like that do not explain what the code is doing.
Wer code should be so clean and straightforward that it doesn't need comment.
If a comment explains just what the code is doing is redundant and a problem with redundant
comments
is we changed the code.
But not everyone is very consistent in changing the comments.
So after a while these comments become outdated and because they don't get compiled like
the code there
is no way to validate them.
And after a while they become useless.
So again keep them to a minimum and explain why's hows and constraints that we had at the
time we
wrote the code.
So the next person who is reading wer code knows the reason why we wrote the code.
That's way

C# is aesthetically type language which means once we declare a viable we need to specify
this type and that type cannot change during the lifetime of that variable.

SECTION 4:

Earlier in this course we'll learn that classes are building blocks of our applications.
These classes combine related variables or fields and functions together.
So here's an example.
In this picture we have a class called person with four fields name age height and weight.
And it also has four methods or four functions.
Walk talk eat and sleep.
This class is a type or a blueprint from which we create objects.
So an object is an instance of a class.
In this example we can create three instances of this person class like John Murray and Scott.
So more accurately when we run wer application it's these objects that are talking to each
other and
collaborating to provide some functionality.
But the world class and objects are often used interchangeably.
OK now let's see how we can create a class in C-sharp.
So to create a class we start with an access modifier and then the class keyword and an
identifier an
access modifier determines who can access this class.
For now don't worry about it because that's something I have covered in my C-Sharp
intermediate course
which is the second part of this course.
Just remember whenever we want to create a class use the public keyword to make the class
accessible
anywhere in wer application.
Inside the code block class we can have variables which we call fields.
Also note that when we declare a variable we need to specify an access modifier.
Again for all examples in this course.
We're going to stick to public and in the next course we'll take a look at other access
modifiers.
Note that in C-sharp anywhere we have a statement like a variable declaration here.
We need to terminate that statement with a semi-colon but we don't have to do that when we
have a
code block.
Wer classes can also contain methods.
So here is an example.
In this example void is the return type or to introduce method which means this method does
not return
any values.
And also note that this method does not take any promotors as indicated by empty parenthesis
so it simply
outputs the name of the person on the console.
Here's another example.
In this example we have a calculator class with one method which takes two parameters of
type integer
and returns an integer.
Now that we have a class let's see how we can create an object.
So earlier we learn that to declare a variable we start with a type and then an identifier
creating
objects or instances of classes is pretty similar.
We start with a type and an identifier.
But there is one more step we need to allocate memory for that object and that's when we use
the new
operator.
So in C-sharp classes are treated differently than primitive types.
So we need to explicitly allocate memory for them.
But the good thing is unlike languages like Objective C or C++ we do not have to worry
about the allocating
that memory.
C-L are our Common Language Runtime will take care of that for we.
It has a process called garbage collection which automatically removes all objects that are not
used
.
So to allocate memory to an object use the new operator and then repeat the type of the class
and practices
.
We can make this code a bit shorter by using the Varg keyword that we learned earlier and
now that
we have a Person object we can access its members like named field or the introduced
method using the
dot notation.
So in this example I set the name of this person and then call the introduced method.
Now let's see what is not static modifier that we saw in our first C-Sharp program.
So here's the calculator class that we saw earlier.
We can modify this method with the static keyword like this and as a result we can access
that method
directly by the calculator class itself.
We do not have to create an object to access a static member.
In fact we cannot access static members from objects.
So what is this all about.
Why do we need this.
Well let me show we what's happening behind the scene and then we will have a better
understanding
of this.
So without the static modifier when we create three objects of this calculator class each
object in
the memory will have the add method.
But when we apply the static modifier the add method will be only in one place in memory
and that is
the calculator class itself.
So it's not going to be repeated three times in memory.
By the way do we need this.
We use the static modifier when we want to present a concept that only a single instance of
that should
exist in memory.
Here's an example.
Remember the Program class in our first program.
So there we had a main method and Main was modified with the static keyword which means
there is only
one instance of the main method in memory.
There is only one entry point in each C-Sharp application.
Current day time is another example.
We don't want to have multiple date time objects in memory each representing a current date
time.
We want only one place in memory where we can look at the current data.
So all I want we to know for now is that when we modify any members of a class whether it's
a field
or a method with a static modifier that member will be accessible from the class itself not an
object
.
Well that's we know three for now.
Let's flip over to Visual Studio and do some coding

OK here I have a blank console application and I want to create a class called person so we
can create
a class here inside the main method because that's a function or a method.
So we need to create a class at the namespace level.
So look here we have a namespace and here's one default class.
We can create another class at this level.
So public class person code block.
Now listicle are a couple of fields so public string first name public string last name I as
declare
a method Pawlick void which means it doesn't return any values introduce.
And here I simply use console the right line to output the full name of this person on the
console console
.
Dot writes line.
My name is first name plus I would like to add a space between them and last name.
Nounless create an object of type person.
So we go to the main method.
We can start with person let's call this John equals new person I know the green highlight
here resharpen
is suggesting to use var to make this code a bit shorter and cleaner.
So I put the cursor here Altan enter and enter.
Now let's set the first name and last name for this object.
So John dot first name he calls John John that last name.
He calls Smith.
I know we can call the Introduce method.
Let's run the application control and F5.
So my name is John Smith.
OK now let me show we something.
When we write a real world application we're going to have tens hundreds or even thousands
of classes
.
So we're not going to put all of these classes inside this file here.
Otherwise the file will explode.
So we want to have one class profile.
If we have the sharper We can easily move this class to a new file.
So all we do is put the cursor on the class name press Hultin enter and not the first option.
Move to person that see us enter.
What happened was resharpen automatically created a new file called person that's yes and
move this
class from program that c file which was here inside the new file.
So I didn't have to go manually create a new file and type the name of the cluster but if we
don't
have sharper it is perfectly fine.
So to add a new cluster of project go to solution explorer right click on wer project then go to
add
.
Actually we can see that here let me drive the solution explorer to the left.
OK.
Right click on that class or we can use the shortcut shift.
And see.
Now I just don't have to type the name of wer class let's say calculator.
That's it.
Now we got a new file here calculator.
Yes.
And here's a class.
Note that in this example because the name of my project is C-Sharp fundamentals.
Every time I create a class by default it's either inside the seashore fundamentals namespace
and the
introduction of this course.
I explain that we want a group related classes inside different name spaces so perhaps the cost
of the
person is different from calculator calculator is more about math.
Whereis person could be part of a commerce application.
So a better way is to Right-Click the project go to add new folder.
We create a new folder like math.
Then we moved this calculator cluster confirm.
The only problem is when we move the namespace is not changed by default.
So we need to go here manually and Daut math here.
Or if we have resharpening we don't have to even type that.
We can put the cursor on the name space and press alternate enter and enter.
And that automatically updates namespace the C-sharp fundamentals that math.
So here's our calculator class.
First we add the public key word so that it's accessible.
No that if I don't I die and I go to program that C-s I'm not going to be able to create a new
instance
of calculator.
So if I type calculator calculator the intellisense cannot find that class because it's not
accessible
.
Now we go to the calculator at the public key word here.
Back to the program
and resharpen is suggesting to import that calculator class which means adding a using
statement on
top of this file.
So with resharpen I can press Altan enter and I would automatically add this using statement
here.
But if we don't have sharper We have to go on top of the file manually type the name of the
namespace
where that class is declared.
So using C-Sharp fundamentals that math.
So we see resharpen makes coding a lot easier.
We're going to have to worry about these name spaces.
What class is in what namespace.
And we don't have to type them we just type the name of wer class and Lady sharper.
Do all the plumbing for we.
OK.
Now we have a calculator class let's create an object
and we use the new operator to allocate memory to that object.
And I just realized that we didn't have any method to this class.
So let's get back there.
Let's create a new method called that which returns an integer and takes two prime emitters a
and b
.
And it simply adds them together and returns them.
Now we save the file with control and as get back to program a quick way of doing that is we
press
control and tap and we can switch between the open windows in Visual Studio.
So we don't have to grab the mouse every time and click these tabs on the top.
We can do everything with wer keyboard.
So back to program.
Yes.
And here we call the ad method.
We pass two arguments one and two.
We can store the results in another variable var result = and we can output that variable on the
console
console.
That great line result.
Now let's run the application with control and F5.
So the result is three.
Now before we finish this lecture I want to show we something interesting here.
Look every time we use console died right line we access that method directly on the console
class itself
.
What does this mean.
That means the right line method is defined as the static.
We don't have to go and create a new console object in order to call the right line method.
So we all use a static modifier before without being aware of that.
In this case all method of the console class are declared as study because we only have one
console
when we run the application.
That's it for this lecture.
I hope we enjoy it.
And thank we for watching

In C-sharp we also have another type similar to classes which is called structure or struct.
So in terms of syntax it's very similar to a class.
The only difference is in sort of using the class keyword we use the struct keyword.
So similar to classes structures combine related fields and methods together.
But what is the difference if I read the C-sharp documentation.
We're going to see lots of tiny differences between classes and structures and we're probably
going
to be even more confused than when we started.
I personally don't find these subtle differences very pragmatic.
In fact in the real world 99 percent of the time we will create new types using classes not
structures
.
The pragmatic guideline I give we in this lecture is use structure when we want to define a
small
lightweight object like this.
RG recolor here or if we're dealing with something like a point that has an X and a Y we can
certainly
define that using a class.
There is no problem at all.
But if we're in a situation when we want to create thousands or tens of thousands of objects of
that
type it's more efficient to define them as a structure.
If not don't worry about it.
Just stick to classes because that's what we use most of the time.

Another non-permissive type we have in C-sharp is array and this lecture I'm going to give
we a brief
introduction of our age to get we started.
Later new scores course we have a separate section about arrays and there I will cover more
details
.
So what I'm covering this lecture is what is an array.
How to declare and initialize arrays and how to access array elements.
So what is an array an array as a data structure that we use to store a collection of variables of
the
same type.
For example imagine we would like to work with three numbers.
So instead of declaring three integer variables like number one two three we can declare an
array and
call it numbers.
No the square brackets here.
The first one is used to tell the compiler that we would like to declare an array.
And the second one is used to set the size of mothery.
So in C Sharp arrays have a fixed size which means we need to specify during declaration
and it can
not be changed.
Also note the new operator here.
When declaring an array we need to allocate memory for it.
And that's why we need to use the new operator also.
An array isn't an object behind the scene.
So in short we have a class called array.
And when we declare an array using this syntax here internally the compiler creates an
instance of
that class.
So an object.
And that's why we need to allocate memory for it.
Now that we have an array we can access its elements using an index that we supply in the
square brackets
.
Nobody in C-sharp arrays are zero indexed which means the first element of an array has the
index of
0 if we know ahead of time the values we would like to store in an array we can use the
object initialization
syntax and make this code shorter.
So during the declaration we supply the values in curly braces again.
This was a quick introduction to arrays so we can get started quickly and write some simple
programs
.
I'm going to cover arrays in more detail in a later section in this course.
Now let's flip over to Visual Studio and do some coding

OK in this video we're going to take a look at how to declare and initialize an array in C#.
So let's say we would like to create an array of integers.
So we started with and we used the square brackets to indicate that we would like to create an
array
not just an integer.
We give it an identifier or a name.
I know we need to allocate memory to it.
So we use the new operator and repeat into array again.
By this I would need to specify the size of the array.
So let's say three.
Now we can make this code a bit shorter by getting rid of this entire array here and just using
var
.
The compiler knows that number is assigned to an integer array as we see here.
So there's no need to repeat that twice.
Now I'm going to set the first element of this array and because in C-sharp arrays are zero
indexed
the first element starts with index of 0.
So numbers of 0 because 1.
Now let me show we something.
I'm going to display all the elements in disarray on the console so kaso the right line numbers
of 0
and I'm going to duplicate this line a couple of times with Control D which is one of
resharpen shortcuts
and I change the index on each line.
So this is a very basic way of displaying elements in an array and more efficient ways to use
a loop
.
And that's something we're going to look at in the next section.
Now let's run this application and see what happens.
So our array has three elements and the first one is initialized to 1.
But what about the others now that they are initialized to zero by default.
So that means when we declare an array all the elements are set to the default value of the
data type
for that array.
In this case because our array is of type Integer the default value for integers or any kind of
numbers
in C-sharp is zero.
If we had an array of booleans all elements in that array would be initialized to false.
Let's try that.
So I'm going to create another array.
Let's call it flags.
And this time I'm going to use a bully array.
Again the same size again Similarly I said the first element of flags of zero holds true and
only display
all elements in disarray.
Let's run the application.
So note that the first element of the boolean array is set to true.
But the second and third elements are false.
Now one more example.
Before we finished this lecture this time I'm going to create an array of strings and I'm going
to use
the object initialization syntax to initialize it during declaration.
So I'm going to call it names new string array of size 3 and I'm going to store three names
here.
So Jack John and Mary.
So with the object initialization syntax we start with curly braces and it's supply values for
each
element of the array.
That's pretty much it for this lecture.
Later in this course we're going to have a full section on arrays and there I'm going to convert
arrays
in more detail.
I hope we enjoy this lecture and thank we for watching

OK in this video we're going to have a quick introduction to strings so we can quickly get
started
.
And later in the course we have a separate section where we cover more details about strings.
So in this lecture I'm going to cover what is a string.
Different ways to create strings and sure.
And finally I'm going to talk about escape characters and verbatim strings which are pretty
handy.
So if string is a sequence of characters and as we can see in this example in C-sharp which
surround
strings with double quote as opposed to characters which are surrounded by single quotes
there are different
ways to create strings and share a very common way is to use a string literal.
So just like declaring a viable we started with a type.
And in this case string then an identifier.
And finally we assign it to a string literal.
We can also concatenate strings using the plus operator.
So in this example I'm adding first name plus a string literal which represents an empty
character.
And finally the last name.
Sometimes using string concatenation this way can create a bit of noise in wer code.
We might have different string variables that we're concatenating and it's hard to visualize
what
the output looks like.
If that's the case we can use string format.
So in C-sharp this drinky word maps to the String class in the Dot Net Framework and we
learn that
classes can have fields and methods and we can declare these members as the static which
means we can
access them directly on the class without the need to create an object.
So in the example we see here recalling the formatting method on the string class format is a
static
method.
So we can directly access it using string dot format.
This method takes a couple of parameters.
The first one is a format string which we use to define a template for a string inside this
template
.
We have placeholders placeholders are indicated by curly braces and they're Ziering next.
So here placeholders zero will be replaced by first name and placeholder one will be replaced
by last
thing.
So as we see in this example it's much easier to visualize the output as opposed to
concatenating multiple
strings together.
Sometimes we might have an array of objects.
We can create a string from combining all elements of that array using a separator.
So in this example we have an integer array with values 1 2 3.
And in the second line we are calling the join method of the String class which is a static
method and
we supply two arguments.
The first argument which is a string is a separator.
In this case I would like to combine the three numbers using a coma.
The second argument to this method is the array whose elements we would like to combine.
Now that we have a string we can access each of its individual characters using an index.
So in this case name of zero represents the first character in our string.
One thing we need to know about strings and C-Sharp is that strings are immutable which
means once
we create them we cannot change them.
So back to our example here we can certainly read the value of the first character in our string
but
we cannot change it.
So the third line here which is indicated by read is not going to be compiled.
There are methods in the String class that allows us to manipulate strings and modify their
values.
But all these methods return a new string so the original string is not changed and that's what
they
mean by immutable.
There are a few special characters in C sure that sometimes have different meanings.
For example if we want to have a new line in wer string we need to use backslash then when
the compiler
sees that it automatically as a new line if we don't add the backslash the compiler sees it and
just
as the letter N same for tap if we want to have a type we use backslash T.
Now that brings us to an interesting situation.
What if we want to use the backslash letter itself because when the compiler sees backslash it
thinks
we are using a special character so it's not quite sure.
It might get confused.
So if we want to tell the compiler that do like to use the backslash letter we need to represent
that
byte double backslash same for a single quotation mark and double quotation marks.
We need to prefix them with a backslash.
And that's what we call by as scaping characters in C-sharp.
But these are special characters.
The list of special characters in fact is even more than that.
But personally I have not found any of those special characters that we find in search of
documentation
.
Pragmatic those we see in this table are the ones I have found very common.
OK now because of these special characters there are cases where creating a string can be a
little bit
messy.
For example look at this path variable here know that all these double backslashes we have it
looks
a little bit messy doesn't it.
The good thing is in short we have a kind of string which we call verbatim string and with a
verbatim
string we don't have to use all these double backslashes we can simply prefix our string at
sign and
as a result we can get rid of all this double backslashes and just use a single backslash.
OK.
Now just flip over to Visual Studio and do some coding

OK let me start by creating a string called first name so string first name because mush.
Now obviously here we can use the Varn key word because compiler knows we have
assigned this valuable
to a string literal so that should be of type string so we can make the code shorter.
So I put the cursor here.
I can manually change that to var or would be sharper Altan enter and enter.
Now let me show we something interesting here.
Cover wer mouse over the marquee worth.
Note that this fireball is of type string which is a class that is defined in the System
namespace in
the lecture about primitive types.
I explained that all primitive types in C-sharp map to type in the Dot Net framework.
For example let's use that end and declare a variable like number.
If we have wer mouse on end we see that's of type in 32.
I know that this in 13:2 is the structure.
So all these keyboards we use in C-sharp like ain't char string float bulled they're all mapped
to a
type in the dot net framework the primitive types are all structures like this and or in 32 but
the
strings are classes.
So let me remove this.
Look at this one more time.
So we have a class in the System namespace which is called string.
What this means is we can create a string like this using the string keyword in C-sharp or we
can
use the string class in the Dot Net Framework.
The difference is when we use this string class we need to import that namespace.
The System namespace on the tongue.
Because here we are writing code inside this namespace but we are accessing a class that is in
a different
namespace System namespace.
So if we have resharpened we can automatically import that.
Otherwise we have to go on top of the file and type using system and call it.
So whether we use the string class like this example or using the string keyword
it's exactly the same.
There is no difference.
And that's one of the things that confuses beginners too C-sharp.
Similarly we can create an in 32 using the int32 structure in data framework.
Call it I or we can use int keyword.
They're essentially the same thing.
OK now let's clean up all the extra noise here and get back to our example.
I'm going to change just two var to make the code cleaner.
So one way to create a string is to use concatenation.
So we can declare another string and concatenate three strings together.
But as I explained sometimes it's hard to visualize the output and we can use the string format
method
.
So here is an example.
So string again maps to a system that string class and this class has a bunch of static methods
as we
can see here.
So these methods are accessible without the need to create an object they're accessible
directly on
the string class.
For example we can use the Compare method to comparing strings.
In this case we're going to use the format method.
So this method takes two arguments.
The first one is a format string or a template something like this.
And the other arguments are values to apply to this template.
So I'm going to pass first name and last name at runtime.
What we have here will be replaced by first name.
Same what we have in here will be replaced by last thing.
Now let's take a look at string that join.
So I'm going to create an array of names
and I'm going to create a string by combining all these values using a comma as a separator.
So
we use the join method again a static method on the string class.
The first argument is a string which represents a separator.
We can use coma.
And the second argument is the array.
So names let's display the result on the console.
So formatted names just like that.
So we see John come on Jack.
Come on Mary.
This is a very useful technique when we have some values and we will like to combine them
together
using a separator.
Now let's take a look at verbatim strings.
So I'm going to create a string that has multiple lines and has a few paths.
So something like this
.
This string is very unreadable.
So we see the output first.
And then I'm going to show we how we can clean this up using a verbatim string.
So instead of displaying formatted names I'm going to display the text year
.
So this is the output.
Hi John.
Then on a new line look into the falling pants then on to new lines.
We have two paths here.
As we see using a normal string is very hard to format something like that.
So we can use a verbatim string.
All we do is we prefix it with and that's fine then we don't need backslash n we can simply
put down
on a new line.
Same here.
Remove the max Leshin on a new line and we can remove all these double backslashes
.
So we see it's much easier to read and understand history.
So whenever we need to use backslash newline or tab use a verbatim string to properly
formatted string
.
So that was a quick introduction to strings to get we started later in this course.
We have a separate section where I cover more details about working with strings.
I hope we enjoyed this lecture and thank we for watching.
OK and other types are going to cover and the section is enums.
An enum is a data type that represents a set of name value pairs or constants.
Let me show we where we use nums in the real world.
Imagine we're building an application for a Post Company and we want to support a few
different shipping
methods.
So one way is to declare a few constants each representing a shipping method.
And in wer application based on the shipping method we can make decisions to calculate the
shipping
costs or the tax or display different messages to the user.
So the possibilities are endless Now even though this approach works it's a little bit messy.
It's better to define a new type where we can represent different shipping methods.
So that's where we use an enim so we can create a new enum called shipping method with
these three members
.
So in simple words use enums where we have a number of related constants and sort of
declare multiple
constants declare an ino.
This will be a new type in wer application just like we have classes or structures.
OK now that we have any we know we can use it with the dot notation.
Now one thing I wanted to know here is that an ether is internally an integer but if we have a
reason
to change that and use a byte instead perhaps it could be easier for we to map in wer database
columns
then we can specify byte during declaration of wer name.
So that's the basic idea.
But now let's flip it over to Visual Studio and let's see how to work with gnomes and how to
convert
them to numbers and strings.

Okay now I'm going to create a new noom called shipping method.
Note that because enim is a new type we need to define it at the namespace level.
So
now if we don't set any values to the members of this new the first member is going to be
automatically
set to zero.
And from there every member's value will be incremented by 1.
Now in terms of best practices I suggest always explicitly set values for these E-News
because it's
very likely that somewhere in wer database we might have a table that represents this enim.
So we want to make sure the IDs are the values we assign to these new members match to the
records
we have in the database.
If we rely on the automatic value assignment and sometime in the future add a new member
to this new
the value of some of the existing members may change and may no longer match the records
in the database
.
So
OK now we have a new we know it's a new type and we can use it when declaring a variable.
So in the main method
and here we use the dot notation.
Know that Intellisense shows us all the members and this we know.
So let's set it to express.
Now I told we that internally and Ino is an integer.
So I can easily cast that to an integer.
If I want the numeric value of this U.
So let's display the numeric value of this shipping method on the console.
So I put Methot here and then cast it to an integer.
Let's run the application.
So the value of Express is three.
Now there are times that we receive a number from an other system.
It could be wer database or it could be a third party application supplying some data and we
need
to convert that number that integer to a shipping method in wer application.
In situations like that again we can use casting to convert an integer to a shipping method.
Let me show we what I mean.
So imagine we received the number three from somewhere else
and we want to convert that to a shipping method so we can use casting shipping method and
put method
id here.
Let's look at the result.
So we see the number 3 represents the express shipping method.
So these are two examples to convert anti-New to and from an integer What about the strings.
There are times that we need to convert and to strings or get us rank and convert it to an
enim.
Let's take a look at two more examples here.
So I'm going to convert this method here.
Do we drink so Method dot look at these methods here.
Every object in C-sharp has a method called two string.
So technically we can convert anything to a string without doing any extra work.
So all I have to do here is just to call the two string method and when we run the application
we're
going to see Express on the console.
There we go.
Look at the third line.
OK.
No as a tip.
Cancel that right line by default.
Always calls that two string method on any value wer password tweet.
So in this example even if I didn't call to string console the right line would still convert that
to
a string.
But in case we're not using console the right line and we want to explicitly convert that enim
to
a string then we can use the two string method.
So I'm going to revert this back and find example when we have a string.
And we want to convert that to an enim.
Again the reason could be we have that string stored somewhere in the database or in another
system
.
So something like this we need to convert this method name to a shipping method
enumeration.
How do we do that.
Well before I show we that I want to introduce we to a new term parsing parsing.
In programming means getting a string and converting that to a different type.
So we say we parse the string.
Which means we convert that string to a different type.
So technically here I want to parse the string into a shipping method.
How do we do that.
Well we have a class in Dartmouth called ino.
This class is defined in the system namespace.
So if we don't have using system on the top of wer file we need to add that here.
Now this class has a number of static members.
So if we put dot here we can see it's static methods.
And look here we have a method called parce.
Let's look at the parameters of this method.
So open the parentheses again.
So this method has two versions which we call two overloads.
The first one takes two parameters.
The second one takes three parameters.
Let's take a look at a simpler one.
So the first promiser is a type object.
What is a type type is a classic Achmat that represents mental data above other types.
As a pragmatic tip whenever we see that type object we can use that type of operator.
So look type of this is a Keyworth.
This is an operator and takes a parameter.
So here we need to specify the target type that we want to convert the string to.
What is the target type here.
Our shipping method so shipping method here.
Now look at the second parameter of this method string value.
So here I pass method name.
Now look at the return type of this method.
It returns an object.
It does not return a shipping method.
So we need to cast this object to a shipping method which means I go to the beginning of the
line.
Use cast wer shipping method.
I know I can store the result of this expression into a different variable.
Let's call it shipping method.
Or forgot the semicolon.
There we go.
Now if I hover my mouse over var look the type of our variable is a shipping method.
So this is how we convert or parse a string to an enum or enumeration
OK so far we have talked about various data types and C-sharp.
We looked at primitive types like a major character float pool and a few known primitive
types like
classes structures arrays and strings.
And I told we earlier that both strings and arrays are classes.
So I showed we during one of the demos that this drinky word master the String class and
that and same
goes for the array notation that maps to their A-Class.
Now that brings us to an interesting topic.
And C-Sharp essentially we have two main types from which we create new types.
We have classes on one side and structures on the other side.
So every time we have learned so far is either a class or a structure.
So all primitive types are structures.
Remember I told we use the structures for small types like our G-B color and point well all
primitive
types are very small types.
They take no more than 8 bytes.
That's why they are internally defined as a structure in dot net arrays and strings are both
classes
.
We can also create custom classes like person or calculator.
Now in C-sharp these classes on structures are treated differently at runtime in terms of
memory management
.
And that's what I'm going to cover in this lecture.
I want we to understand what happens under the hood in memory.
So if wer program does not behave the way we expect we'll be able to troubleshoot it.
Structures are what we call value types while classes are reference types.
When we create a variable that is a value type a part of memory called Stack is allocated for
that
variable.
This memory allocation is done automatically so we don't have to worry about it.
When this variable goes out of scope it will immediately get removed from the stack by
runtime or C-L
or with reference types however we the programmer need to allocate memory werself.
Remember the new operator we use the new operator with classes.
So when we use the new operator we tell the runtime to allocate memory to this object.
And this happens from a different area of the memory called heap memory on the stack is
more sustainable
.
So if we create an object and that object goes out of scope it will continue to exist in the heap
for
a little while.
It won't be removed immediately.
There is a process called garbage collection which is done by runtime or C-L or that takes
care of this
.
So once in a while still are looks at the objects that are no longer used and removes them
from the
heap.
Now this was the theory behind value types and reference types.
What do we need to know in pragmatic terms is when we copy an object to a new variable
depending on
whether that object is a value type or reference type.
There will be two different outcomes and it's much easier to show this in code.
So let's flip over to Visual Studio and see how copying value types and different types are
different

OK in this video I'm going to show we a reference types and value types in action.
I'm going to use two different examples so I'm going to start with a simpler one.
First I'm going to create an integer variable
so I use 10.
Now I'm going to create another variable called B and copy A to B.
And finally I'm going to increment B by 1.
So I'm going to use the increment operator.
Now I got a question for we.
What do we thing the value of 8 is going to be at this point.
Is it going to be 10 or 11.
The answer is 10 because integers are value types.
So when we copy a value type to another variable a copy of that value is taken and stored in
the target
location in memory.
So let's verify this.
I'm going to use cancel the right line.
And here I'm going to display a and b on the console.
What is a good way to display and B we can use string format remember string format so
string not format
here resupply a format string.
So 0 and 1 here are placeholders and so play arguments to fill these placeholders.
So A and B here.
Now let's run the application with control and F5.
So look at use 10 and 11.
So the lesson is when we copy a value type to a different variable.
A copy of that value is taken and stored in the target variable.
That's why we call them value types.
Their values are copied.
Let me show we what just happened in memory.
So imagine here is the stack.
And somewhere in the stack we have a location identified by a.
And in that location we have the value 10 when we copy to be a new location in memory and
stack is created
identified as B and the value we had there in a is copied to be.
That's why these two variables are now completely independent and making a change to one
does not impact
the other.
Now let's see.
Reference types in action.
So this time I'm going to create an integer array.
And as we know in C-sharp an array is a class.
So it's a reference type.
So let's create array one
on here.
I'm using the object initialization syntax to initialize my array with one two three.
Now I copy this array one into another variable called array 2
and finally I'm going to make a modification to array 2.
So let's say I want to set the first element to zero
at this point what do we think is going to be the first element of array 1.
Is it going to be 1 or 0 it's going to be 0.
Let's go back to the memory visualization again and see what happens when we run this code.
So here we've got stack and heap.
When we create and initialize array 1 this is what's going to happen first an object is going to
be
created on the heap.
This object is in a memory location with that address.
We see here and inside this memory location we have the actual array with three elements.
One two three.
Next the runtime or ACL are create a viable on the stack identified as array one the value
inside this
variable or inside this memory location is a memory address and that's the address of the
object on
the heap.
The actual array.
So array want points or references.
The object on the heap.
So this is what happens when we create and initialize array one.
Now let's see what happens when we copy array 1 to 2.
So the runtime creates another variable on the stack identified as Array 2 and again inside this
variable
.
We're going to have a memory address.
And as we see in this picture this address is the address of the object on the heap.
That's why both array 1 and array 2 point to the same object.
Which means when we make any changes on this object on the heap either through every one
reference or
array two the changes are visible through the other variable.
That's why we call these types reference types.
So when we copy them there reference or their memory address is copied.
Now the actual value.
So back to the code.
Let's verify these.
Again I'm going to use Konsole the right line on the string the format
so I'll display the first element of both are A1 and array two and they both should be 0.
That's running application.
They both are zero
OK let's take a look at another example of reference types and value types in action.
So in this code I have defined a class called person with one field called H.
And inside our program class I have defined two methods increment and make Allt the return
type of both
these methods is voit which means they don't return any values.
And the reason I have defined both these methods of study is simply to call them without the
need to
create an object.
Just want to keep things simple.
So in the main first I'm going to create an integer called number
and I set it to 1.
Now I'm going to call the increment method and pass my number viable as an argument.
So the Inkerman method takes a parameter of type integer called number and adds 10 to it.
Note that here I'm using the addition assignment operator to add 10 to the number that is
passed to
this method.
Now at this point what do we think is going to be the value of our number in the main
method.
It's going to be one because this is a value type.
And when we passed these variable as an argument to the increment method a copy of this
variable is
taken and sent to the Inkerman method.
So interestingly even though these two variables have the same name but there in two
different locations
in memory one is the number with the scope of the main method.
So outside the main method this variable does not have a meaning.
And here we have another number coincidentally have the same name.
Inside the Inkerman method but that's a different place in memory and its scope is limited to
the Inkerman
method.
So when this increment method is called that new location is created called number.
Its value is incremented by 10 and then it's immediately destroyed.
Now let's verify this.
So I want to use console the right line and display number.
We run the application.
So our number is 1.
It's not affected by the increment method.
Now let's take a look at an example of a reference type.
So this time I'm going to use our personnel class.
So I create person object
and used the object initialization syntax to set its field.
So this person is 20 years old.
Now here we have another method called Make old that takes a person object and adds 10
tweets age of
field.
So note that here because the type of this parameter is a reference type the object that is going
to
be passed here is not going to be copied.
Each reference is going to be copied.
Which means both the person object we have the main method and the person object that we
have as a parameter
to this method will be pointing to the same object on the heap.
OK so if we call make old and past this person object upon returning from this method the
age of this
person is going to be 30 let's verify that.
So person the age and just run the application.
There we go.
That's it for this lecture.
I hope we enjoy it.
And thank we for watching

So in this section we learn that we have two main categories of types in C Sharp on one side
we've
got crosses on the other side we've got structures examples of class those are strings arrays
for any
custom classes that we create.
Examples of structures are all the primitive types like integer character float and any custom
structures
that we create.
The difference between the two types is purely memory management and we can review that
again in the
lecture hall reference types versus value types.
Now from the next section things start to get really interesting because I'm going to teach we
about
control flow and we'll be able to write simple C-Sharp programs and then in each section we
will learn
something new about C-Sharp and we'll be able to write more interesting programs.
So I was here the next section

Section 5:

This section we're going to explore conditional and iteration statements and C.
We use these statements to control the flow of programs.
So from this section we're going to start writing simple SUKAR programs.
Now I have designed a number of programming exercises that we can find at the end of this
section Whether
we're new to programming or been programming for a while.
I highly recommend we to spend half an hour if we are going through these exercises because
not only
will they help we remember the language syntax.
It will also train wer programming brain which is absolutely crucial if we want to be a
successful
programmer.
So go through the lectures and spend some time doing the exercises.
Now whether we solve the problem or get stuck I think still a good idea to look at my
solutions as
a different way of solving the same problem.
By the way my solutions are by no means perfect.
In fact there is no such thing as perfect in programming.
We give a problem to 10 different developers and each comes with a different solution.
So do wer best to solve the problem.
I look at my solutions for inspiration.
Now let's get started.

OK we got to conditional statements in this lecture.


We're going to talk about the language constructs of C-Sharp that are used we're controlling
the program
execution and C-Sharp we have two types of conditional statements.
We have else.
And we have switch and case we also have a conditional operator which is basically a short
way of writing
an infant else.
Let's take a closer look at each of these statements.
Here's the basic structure of if statements with if we always have a condition which is
enclosed in
prothesis followed by a statement that will be executed if the condition is true.
We can actually have an LCF with another condition and again another statement that will be
executed
if the condition is true and optionally we can have an Elsin statement.
So if none of the earlier conditions is true then this piece of code will be executed if we have
more
than one line of code after if or else statements we always need to enclose them with curly
braces.
We can also use that if we have only one line of code.
We can also nest if statements inside each other.
So here as we see I have got an if statement.
And inside this body I've got another if an else statement.
Now one thing I want to warn we is to avoid using multiple nested if statements multiple
nested if
statements result in code that is hard to read are to understand hard to maintain and hard to
test.
So that's what we call a code smell.
And that's something we should avoid at all times.
So each is slightly different from if with if we usually have a condition that is evaluated and
if it's
true and some piece of code will be executed with switch however we have a valuable and we
compared
the value of that variable with different values.
So in this case I have a switch on a variable here called Roll which is an enumeration.
I have two case statements here.
At least we should always have one but we can have more depending on wer circumstances.
So I'm comparing the value of roll with this one here roll down the admin.
So if the rollies is admin then this piece of code will be executed.
And note that each case statement is terminated by Brecqhou statement.
Then I have another case statement.
So if the role is moderator then this piece of code will be executed.
If none of these conditions is true then the default block would be executed.
And of course we need to have a break statement here as well.
Now let's jump in to code and explore each of these cars trucks in action

OK first I start by defining a viable and call it hour and send it to 10.
My intention is to define hour as a 24 hour time format.
Now I can say if our is greater than zero and it's less than 12 Konsole right line.
It's morning.
So as we see I put the expression here that is a boolean expression I'm using and here.
So these two conditions will be evaluated and if both are true then these will be executed.
Now I can have another condition.
So I write.
Else if our is greater than or equal to 12 and it's less than 18 which is 6 pm right line
afternoon
.
And finally I can have an else statement.
So if none of the earlier conditions is true then this piece of code will be executed.
So it's evening as I told we if we have more than one line of code we need to enclose them in
curly
braces.
But some people say even if we have one line of code it's good practice to put them in curly
braces
like this.
Similar here
they go.
Let's run this program is in control and F5.
So it's morning.
In this case because the hour was 10 this condition was evaluated and it was true.
So this piece of code was executed.
Now let's take a look at conditional operator.
I'm going to change this piece of code.
So first let me clean this up with the sharper we use control and double we to select some
piece of
code like this.
It's really easy.
It's much easier than putting the cursor here and using shift and down arrow like that.
So anywhere we are in the code we can just control w to select a piece of code or keep
extending wer
selection like this.
OK.
Now let's take a look at conditional operator so I can define a ball.
Say is gold customer and set it to true.
I want to say if is gold customer I want to have a float here.
Call it price.
And here I say price is going to be nineteen ninety five dollars.
Otherwise price is going to be twenty nine ninety five dollars.
Now I can rewrite this code using a conditional operator.
So I would say float price equals put the condition.
Here is gold customer followed by a question mark.
Now if that condition is true what do I want I want.
Nineteen ninety five dollars else is specified using a colon.
The price is going to be twenty nine ninety five dollars.
And of course I can't get rid of this.
I just commented.
I keep it here so we can see them for comparison.
And finally put the price on the console.
So let's review one more time.
That's the condition.
If that's true then what we have after question mark and before the colon will be executed.
So 1995 will be returned and assign to the price variable otherwise is specified using a colon.
And here what we put here will be returned and set to the price here.
So is it just a shortcut to write an IF statement let's run the application.
So the price is $19 because I am a customer.
Now let's take a look at switch case.
So with resharpen I use control and W to select everything here and clean it up.
So actually let me define an enumeration first
public income season.
So we have four seasons.
Spring Summer Autumn and Winter.
In this case we don't really need to give an explicit value to each of these items here because
we're
not working with a database or an external application where there is a numerical
representation for
the seasons.
So if we just leave it like that and to keep my code clean I would like to put this in a separate
file
so we'd resharpen what I can do is I put the cursor here.
And as we see I've got this marker here.
So with Altan enter I can activate that and press enter and move it to another file.
If we don't have resharpened Why do we need to do is to go to solution explorer here.
Right click wer project go to add new item.
And here we select a class to add a new class.
Let's call it Season 2 because I already have a file called season that's yes.
So I put that new class here.
Now I'm using an enumeration model class so I can get rid of this and then I can just go here
and copy
this piece of code and put it into the file here.
So as we see it's much easier and faster to use resharpen.
All right.
I'm just going to get rid of this file
and delete it here.
OK.
So we define an enumeration called season with or values here.
Now let's go to program.
I'm going to define a variable this time I'm going to use var college season.
Set it to season dot autumn.
Now let's put a switch on season so each season.
So we put the variable in parenthesis.
Here we have a block and we can have one or more case statements.
I can say if season is season the autumn display on the console it's autumn and a beautiful
season.
I termly this case block with a break statement.
Now I can have another case statement here if season is summer.
Customer writes line say it's perfect time to go to beach and break.
Finally I can have a default here so if the season is none of his values I can say I don't
understand
that season.
It's a little bit stupid but that's just for demonstration.
And of course we need a break statement here.
Let's run this application now.
So it says it's autumn and a beautiful season.
Now let me show we something.
Let's say in autumn and summer we would like to have a promotion.
So instead of displaying this message here we would like to say something like we've got
promotion and
I would like to have the exact same message appear if the summer if the season is summer as
we see
this piece of code looks like a duplicate.
It's not a good thing.
What we can do here is to get rid of these statements here and have these two case statements
next to
each other.
Note that the first one got nothing next to it and the second one has the actual code that will
be executed
.
So in this case what that means is the if the season is autumn or summer then this piece of
code will
be executed.
Let's run the application.
We've got promotion.
That's it for this video.
I hope we enjoyed it.
And thank we for watching.

OK we've got to itemization statements.


If we have done programming before we know that pretty much every programming
language has a set of
iteration statements which are used for repeatedly executing a sequence of statements in C-
sharp we
have for our iteration statements 4 for each while and do while.
So let's examine the syntax for each of these iteration statements for loops of three parts.
Here's the first part semi-colon second part semi-colon and the third part the first part is what
we
call the initialization clause and that's where we created a counter for controlling the number
of times
the loop will be executed.
So here I have created a counter called I set it to zero.
We're free to use any names for wer counter valuables but I as a common convention.
The second part is what we call the condition clause.
So the for loop here will be executed as long as this condition is valid.
And the third part is what we call the iteration clause.
And here we typically increment or decrement the counter variable.
So here because I said I 2 0 I would increment i in every iteration until it reaches 10.
And inside the body of the four block we have a sequence of statements that will execute
repeatedly
for each is used to iterate over elements of an Enumerable object.
What do I mean by enumerable.
In simple words that means anything that has some kind of list or array nature.
So far we have learned about arrays and the strings and string as we know is a sequence of
characters
so the string is enumerable.
The array type is also enumerable.
So anything that has some kind of list nature is enumerable and we can use 4:8 to iterate over
their
elements.
We can definitely do the same thing with a for loop but doing that with 4 h is easier and
cleaner in
terms of syntax.
Here is one for each block looks like we have a local or temporary variable in this case or call
it
number.
And here we have the in key word.
And here's the list or object that we are iterating.
So assuming that numbers is an array of integers in every iteration number will hold the value
in the
current element of the array.
And C-Sharp we also have y loops in terms of syntax a y loop includes a condition here in
practices
as long as this condition is valid the loop will execute.
Typically we have a counter that we initialize before the while loop is executed and at the end
of the
while loop we increment it.
So as we see it is kind of similar to for a loop but it has a different syntax.
Whether we use for or why loop it's up to we it's kind of personal preference.
And finally we have do while loops do while is a slightly different from while we do while
loop the
loop is executed at least once because the condition is evaluated at the end of the loop.
So here we have do a block of statements that will execute.
We have our counter which we increment or decrement and eventually is the condition.
Now we don't always need a counter with a while and do while loops.
We can use any condition in this lines here.
I used a counter call I to demonstrate that the same thing can be implemented with a for a
while or
with a do while loop.
And finally before we start coding Let me show we two more statements here.
We have break and continue.
So in any loops we can use break to jump out of the loop or continue to jump to the next guy
to ration
.
Now let's start coding and see what all of this means in action.

OK imagine we want to display the list of even numbers from 1 to 10.


So we need to loop to go over the list of numbers between 1 to 10 and for each number we
need to check
the remainder of its division by 2.
And if it's zero that means it's an even number.
So let's start with a for loop
.
So with this loop we said I to 1.
And as long as it is less than or equal to 10 in each iteration we increment I buy one.
Now we need to check the remainder of division of I by 2.
So if that's zero we want to display I on the console just like let's run the application.
So we got 2 4 6 8 and 10.
Now what if we want to reverse this order.
Let's try this program again.
So this time
I'm going to create another for loop but instead of starting from 1 I start from 10
and I change the condition to as long as I is greater than or equal to 1 then I am minus minus
which
means decrement.
I buy one.
Now we are going to have the same condition
cancel the right line.
So let's run the application again.
OK now we see in the second part we start from 10 and then we have 8 6 4 and 2

OK now let's take a look at the For Each loop.


But before we started with that let me write a simple program with for loop and then I'm
going to show
we how for each makes a program cleaner and easier to understand.
So let's imagine we have a strain called name so var name = we set it to John Smith.
So is strange as we know is a sequence of characters.
It's an Enumerable object.
It's like a list.
So we can iterate over that.
So now I want to iterate over the string and I want to display each character on a new line.
So I started with a for loop
.
So I see what's happening here.
This time I'm sitting my counter variable or I to 0 because the index of the first character in a
string
is 0 and I'm going to increment I one at a time.
As long as I eat less than the length of name.
So as we see here each string like name has a property called length which returns the length
of that
string.
OK.
Now let's display each character on a new line.
So consolers right line name of.
Pretty simple right.
Let's run the application.
So that's the alphabet I was talking about.
Now let's see how we can we write the same code using a For Each loop.
So
with 4 h I don't have to worry about a counter variable like I I don't have to set it to an initial
value like 0.
I don't have to compare it against some other value like name that links and I don't have to
increment
it.
So instead we have a variable here called character which in each step of the iteration holds
one character
of the string.
Also interestingly note that in the console the WriteLine we can simply display character
instead of
accessing the character.
I had to give an index in the name variable.
OK.
Now let me comment out our for loop.
So
with control K and control C.
Now let's run the application.
We got the exact same outputs.
So whenever we have an Enumerable object like a string or an array or any kind of list it's
much easier
to iterate over them using a for each.
Let's change this example and I iterate over an array.
So I'm going to clean up everything here.
Now I'm going to define an array of numbers bar numbers
and I'm going to use.
Object initialization syntax to initialize other array with some numbers.
So that looks like this.
One two three more.
So with arrays as we see we have to instantiate them using the new OPERATOR OK.
Now let's iterate over this array for each var number in numbers console dot WriteLine
number.
That's one application.
So as we see for each is an easier way to iterate over a list

OK.
Earlier we wrote this simple program to display the list of even numbers between 1 to 10
using a for
loop.
And they told we during the slides that we can write the same code with for a while or do Y
loop.
So now I'm going to write the same program using a while loop because before we get started
I want to
comment out this code.
So
OK first let's declare a counter variable.
So I.
Is zero while I is less than or equal to 10
now or condition
will display I on the console.
If it's an even number and here we need to increment I buy one.
So this is the exact same code but written using a while loop.
Now in this case I prefer to use a for loop or the scenario because typically we use the for
loop when
we know the number of times we would like to do an iteration.
So it's cleaner to declare that count viable like I.
When we are declaring the four block as opposed to outside the wire loop as we have here.
OK.
Now we might be wondering when do we use the while loop.
Well there is no hard and fast rule but typically it's better to use a while loop when we don't
know
ahead of time how many times we're going to do an iteration.
Let me show we an example here.
So first let me clean up this code.
We want to write a simple code program and this program we're going to display a message
on the console
asking the user to type their name if the user types the name the console is going to repeat or
a code
that name.
But if a user simply presses enter without typing a name the program is going to terminate.
So in this case we don't know ahead of time how many times the user is going to use the
program.
How many times are we going to echo in that case it's better to use a while loop.
So how do we do that.
So in this case we are not going to have a counter variable.
So instead what I'm going to do.
I'm declaring a while and in that condition I'm just going to use True which means this loop is
going
to execute forever.
Let me display a simple message on the console so console that.
Right.
So I'm going to use the right method instead of right.
The difference is the cursor is going to be on the same line.
We're not going to have a line break.
So Type wer name let me run this program and see what happens.
So we see this program is executing forever because that why loop is not terminating and the
program
keeps displaying type wer name.
So let me terminate this.
So at this point we need to read something from the console.
So we use console not the read line method and this method.
Take a look at it signature.
So I remove the parenthesis.
I open it again.
Look at the tooltip.
This method returns a string.
So we can store the result in a string called input.
Now if the user simply presses enter and do not type a name that input is going to be an
empty string
or if that's the case it's the time to jump out of the loop so to check if a string is empty.
We often use string dot is null or whitespace method.
This method expects a string and returns a boolean value.
So if input is null or whitespace then this condition is true.
And then at this point we're going to break and we break.
We jump out of a loop.
Otherwise if that does not happen we want to echo the name.
So cancel the right line echo.
And now we are going to append the input here.
Let's run this application.
So Type wer name.
Marsh echo Marsh.
Note that the program continues execution but this time I type John and it echoes John.
Now this time I'm going to press enter and the program terminated.
One of the questions beginners ask me is how does this press any key to continue up here
here.
I didn't write any code for that.
When we run wer application using control and F5 by default when the application terminates
the console
displays that message for we.
OK now I'm going to change this program a little bit so we can learn about the continued
keyword.
So what I'm going to do here is I'm going to apply and not operator here.
So if the input is not now or whitespace in that case we want to echo it right.
So let's not worry about this break.
I'm going to move this concept the right line here.
Now I'm going to put that break here.
So what do we think is going to happen now.
When we were on application first we get this message type wer name we type a name.
Of course it's not Nailor whitespace.
We're going to get an echo.
But then we get to this statement and that causes the loop to terminate.
So this program is going to execute only once.
How can we change this so it can behave like before.
That's when we use to continue a keyword.
So I'm going to put the continue here and let me explain what happens.
So at this point after we call the name when the program sees this continue instead of
continuing here
it's going to continue to the beginning of the loop.
So we get by here and the condition is true.
So the loop continues to execute.
Let's run the program.
Type wer name.
Marsh.
The loop is continuing.
Type wer name John.
Now this time just press enter and the loop terminate.
So as usual we can write the same program in different ways.
Sometimes we may apply and not operator and because of that we may have to use the break
or continue
which one is right which one is wrong.
There is really no right or wrong.
We need to do wer own judgment which code is more readable and more understandable.

And this video I'm going to show we a useful class we know in dot net framework which is
called random
.
We use this class to generate random numbers.
So first we create an instance of the random class.
This class has a few useful methods.
Next we took turns around a manager next bytes which takes a bite array and fills it with
some random
numbers so we can create a byte array of any size pass it to this method and this method will
fill
that byte rate with some random numbers and next double which returns a random double
between 0 and
1.
Let's take a look at the next method.
This method has three overloads as we see on the screen.
The first one takes no parameters and it simply returns a non-negative random number.
So let's create a for loop and generate a few random numbers and display them on the console
.
OK let's run the application.
So we see some random numbers here.
Now there is something interesting we can do with the next method.
Let's take a look at this method again.
The second overload takes a maximum value.
And the third overload takes a min and max value.
This is very useful when we want to limit the range of random numbers.
So if we want to create random numbers between 1 and 10 we simply supply them here.
Let's run the application again.
So now we have random numbers between 1 and 10.
We can use this technique to even generate random characters like random passwords.
Each character internally is represented using a number.
Because computers don't understand characters and letters they understand numbers.
Let me show we what I mean by that.
So I temporarily comment this out and all I want to do is display a character a on the console.
But I want to cast it to an integer.
We got 97.
So 97 is the standard number to represent a lowercase a in a computer.
This was first introduced as ASCII which stands for American Standard code for
international interchange
.
Let's take a look at this Web site Aski dash code dot com.
So in this table we can see the letters like let me show we here like.
Plus we know all these numbers are alphabets in a uppercase a to that Laura case.
See all these characters have a number represented in decimal format which is here.
And they also have a binary representation.
This is eventually what the computer understands.
Now if we look at 6:51 we see Alora Casey.
And let's take a look at the Zad.
So that is Hundred and 22.
So what this means is if we generate a random number between 97 and 122 and then cast it to
a character
we'll get around no character and we can repeat this a few times and generate a random string
like a
password.
Let's give it a try.
So let's bring this back in.
What I want to change here is limit the range to 97 and 122.
Now if we run this application we are going to get a number coming from the next method.
So we need to cast the true character
and I'm going to change right line to right because I don't want this character to be on a new
line
.
Let's run the application this press any key to continue message is missing up with.
Also let me add a constant the right lane here so we can see more clearly.
There we go.
So here's a random string.
Now a tiny problem with this code is, if someone look at this code.
They have no idea what is 97 and 122.
So let me show we a more expressive way to write the same code.
What we can do is replace that with 0 and 26 because we have 26 characters in the English
alphabet.
Now we get a number between 0 and 26 if we had that number two character eight.
What do we think is going to happen.
Well this is a character.
And internally it is represented as a number.
And when we add this character to a number the result is going to be a number.
Then we cast it to a character.
So eventually we get the same result.
A random character
now in the real world we don't want to create a random string and displayed on the console.
Most likely we would like to store it in a string but there is a tiny problem here.
In the last section I told we that strings are immutable which means once we create them we
cannot
change them.
Of course there are methods that we can play on a string and we get an updated value.
But in every case the original string is not affected.
We always get a new string.
So in C-sharp we cannot create a string and set each individual characters using a random
character
.
But what we can do instead is to store this result in an array and then create a string based on
that
array.
Let me show we how it works.
So
first I declare a character array let's call it buffer.
And because we're are generating 10 random characters here I'm going to set the size of this
or eight
to 10.
And of course we can use var here.
And as we see the green highlight is indicating that the code is cleaner now instead of
displaying
each character on the console.
Because simply stored in the buffer.
So let's get rid of this console right and
store it in the buffer.
So I'm using I the loop counter variable to access an element in the buffer every now and the
last step
is to create a string based on that character array.
Now most of the time we create a string like this.
So we use a string literal but there is a less common way to create a string and C-Sharp is not
something
that we use everyday but it's good to know that as something in wer toolbox so use the new
operator
if we remember from last section the string keyword maps to a string class in the dot net
framework
.
And we know that with classes we can create an instance of them using the new operator.
So we can't do news Stream.
And look here in the constructor of a string we have a few overloads.
The last one as we see here takes a character array.
So if we pass our buffer here we will get a string based on the character orrery.
Now we can display this password which is a string on the console.
Look we've got the same result.
One last thing I would like to add here to improve the quality of this tiny little code and that
is
I don't like this magic numbers here 10 here and 10 here.
The problem with this is if tomorrow we decide to change the length of our random password
we have to
come here and change this 10 to 8 and we have to remember to do this here as well.
So a better way is to declare a constant like password length.
Set it to 10.
We can use that to create our array.
And of course using it in the for loop.
The code is more expressive and more reliable.
So that's all we need to know about random class.
I hope we enjoy this lecture.
And thank we for watching

Okay at this point we know a little bit about race in this section.
I'm going to expand wer knowledge of bag arrays and introduce we to multi dimensional
warriors.
This is useful if we're working with structures such as a matrix.
I'm also going to talk about generic lists which are very useful in building real world
applications
.
Again similar to the last section I have designed some exercises to help we train wer
programming
brain.
So be sure to go through the lectures and spend half an hour doing wer exercises.
Now this started

Earlier in this course we learn a little bit about race in this lecture.
We're going to take a deeper look at race.
So first I'm going to have a quick review of arrays then I'm going to talk about different types
of
arrays we have in C-sharp.
And finally I'm going to introduce some useful methods to work with arrays.
So just to refresh our mind an array represents a fixed number of variables of a particular type
in
C-sharp we have two types of arrays.
Single dimension arrays and multi dimensional race like a matrix.
So single dimension arrays is what we have seen before in this example.
We have an array of integers called numbers and the length of this array is five.
If we know ahead of time the values we would like to store in an array we can use the object
initialization
syntax to initialize that array.
Upon declaration.
So nothing new so far.
Now let's take a look at the types of multi dimensional race.
We have two types of multi dimensional arrays in C Sharp rectangular and jagged race.
So with a rectangular array each row has the exact same number of columns.
So in the example we see in the slides we have an array of three rows and each row has five
columns
with a jagged array.
However the number of columns in each row can be different a different way to look at Jack
array is
an array of arrays.
So we can think of the Jack the array we have in this slide as a single dimensional array with
three
elements and each element is another single dimension array.
Now what's the difference.
When do we use a rectangular array or a jagged array in dot net CLR is optimized around
single dimension
arrays.
So let's say we want to model a matrix is faster to implement it using a jack array than a
rectangular
Arri.
I mean we said that the difference might be really tiny.
Specially with the computers we have these days.
So my pragmatic advice to we is don't get stuck about the difference between rectangular and
jaggery
too much.
Just be aware that in the future we have two types of multi-dimensional race.
Now let's see how we can declare a rectangular array.
So here is the syntax for declaring a two dimensional rectangular array.
So the only new thing we see here is that in the square brackets we need to specify the
dimensions
of the tree.
So in this case this array has three rows and each row has five columns.
If in know the values we will like to stirring this array ahead of time we can initialize this
array
using object initialization syntax.
And if we want to access an element in disarray just like before we use the square brackets.
But we need to supply the index of the row and the column if we want to declare a three
dimensional
array.
We can extend the previous example and supply three dimensions while declaring the array.
So in this example our colors array has three dimensions.
Now let's take a look at the jaggery.
So imagine we want to model an array that looks like this.
So as I explained earlier we can think of this array as an array of arrays.
So at a top level have a single dimension array of three elements in each element.
We have another single dimensional re.
So in our first element we have an array of four elements in the second element.
We have an array of five elements.
So how do we implement this.
Well first we need to declare a top level array not the syntax here.
We use two square brackets to represent it jaggery in the first square brackets we specify the
number
of elements in wer toplevel array.
Now we need to initialize each element of this array to a different array.
So we're supposed to find that the first element of this array is another integer array of size 4
and
to access an element in this array.
Again we need to add square brackets.
So the difference between the Jagd array and rectangular array from the same tactical point of
view
is that we jaggery we have two square brackets whereas with rectangular array we have one
square brackets
.
But we separate the dimensions using a comma in C-sharp.
All arrays map to the array type that is defined in the system namespace of Doc net
framework.
So the array type is a class it has a bunch of properties and methods as we see in this slide.
OK.
Now let's flip over to Visual Studio and see all these concepts in action.

So in this video we're going to take a look at some of the useful properties and methods of
our race
.
Let me start by creating an array of integers and call it numbers.
So in theory numbers equals new in theory and I'm going to use the object initialization
syntax to immediately
initialize Asare So some random numbers here like 3.
Now notice green on the line here.
Sharper is suggesting to use voire to make the code cleaner.
So I put the cursor here Altan enter and enter also here.
Note that it is great out.
Which means it's not necessary.
So we can keep the code even shorter.
So again Alt and enter and enter.
Now let's take a look at the length property
length returns the size of the array.
So in this case we have six elements in the array.
So the size of the array is six.
So cancel the write line
.
Let's run the application.
So we got 6 on the console.
Now let's take a look at the next of method we use this method to find the position of an
element in
the array.
Let's say we're looking for 9 so we can use this method like this every dummy index of.
I opened the bracket look at the tool.
There are different ways to call this method and that's what we call method overloading.
So in this example this method has five overloads or five versions.
I'm going to use the first one which is the easiest.
So look at the first parameter.
That's the array that we're going to do searching.
The second parameter is the actual object we are looking for.
So I press escape past my numbers array here and as the second argument I'm going to pass 9.
This method returns an integer.
So I'm going to store the result in a variable called index.
Let's display index on the console
.
So the index of 9 is 2.
Which means it's the third element in the array because in C-sharp the index of the first
element in
an array is 0.
Now let's take a look at the clear method
.
So this method has three parameters.
The first element is the array.
So I pass numbers here.
The second parameter called index is the starting index of the range of elements to clear.
Let's say we would like to clear the first two items.
So I'm going to pass 0 here as the starting index.
And the third promotor is the length which is the number of elements we will like to clear.
So I'm going to pass two here.
Now I'm going to iterate over this area using a for each block and display all the elements.
So let's take a look at the effect of clear method.
Note that the first two items are set to 0 and that's the meaning of clear.
So in this example because our array is of type integer clearing these numbers means setting
them to
zero.
If we have an array of booleans clearing that means sitting some of its items to false.
And if we have an array of strings or other kind of objects clearing the items in that there are
a means
saying them to now.
OK now let us take a look at the copy method
.
So this method takes three parameters.
The first parameter is the source array.
The second parameter is the destination and the third parameter is the number of elements we
would like
to copy.
So before using this method I need to declare another array
so this is a smaller entry.
It has only three elements.
So I'm going to copy the first three numbers from our numbers are eight in into are another
three.
So
and now just explain the result on the console
and run the application.
So notice that after we the copy method the first three elements in the numbers array which
were here
are copied to a second array.
Now let's take a look at the sort method
.
This method again has five different versions.
I'm going to use the first one which is the easiest.
So I simply pass on another array.
Let's display the result on the console
and or on the application.
Actually this was not a good example because our secondary was already sorted.
So I'm going to apply this sort method on our original array.
So.
And we need to change that in the for each block.
Let's try an application again.
That's better.
So we got 0 0 2 6 9 and 14.
And one more method to explore in this lecture is the reverse method
.
OK let's run the application.
So here is the effect of the reverse method.
OK.
Before we finish this lecture through a couple of things I need to point out here the first one is
look
at the first example where X is the length property of the numbers object whereas in other
examples
all the methods we called like Index of what's called on the array class itself not the numbers
object
.
So what is the difference.
The difference is if a method is accessible on the class itself like array that means it's a static
method.
We're going to take a look at the static members later in this course.
For now just remember when a class member like a method or field or property is declared as
a static
that means it's accessible from the class itself but otherwise that member is accessible via the
object
.
So let me show we an example here.
If I type array dot These are all the starting methods defined in the array class.
But if a type number is dot These are the members that are not static.
There are instance members which means they're accessible by an object.
So if I type it in X of here we see there is no method called index off or if I typed clear there
is
no such a method called clear.
That's why it's only accessible from the array class.
Now we may be wondering how did I know which member is a static and which member is
not.
Well part of that is experience.
But if we try to access a memory and we can find it wer best help is Google simply go to
Google.
Now let's say we are looking for the sort method of the Array class.
Simply type C-Sharp or a sort.
And the first method pretty much in every single case is the documentation on the MSDN
Microsoft Developer
Network.
So if we go here
this is this standard documentation of the sort method of the Array class in darkness
framework.
So we can see all different ways of calling this method.
That's what we call overloading remember.
So a method can have different overloads which means it has different versions.
So note that all these methods have a red as in front of them.
That means it's a static method.
Now let me show we the array class itself.
So if we scroll down we go to air class
I know that these properties here they don't have that red S which means they're not static or
instance
members for instance properties.
I look most of these methods except clone and copy to here are static.
So whenever we get stuck to jump on google type C-Sharp and then type the name of the
class and the
name of the method.
I hope we enjoy this lecture.
And thank we for watching

And the last lecture we learn about a race we learn that in C-sharp arrays have a fixed size
which
means once we create them the size cannot be changed.
But there are situations where we need to work with a number of objects but we're not sure
ahead of
time how many of those objects we're going to work with.
That's where we use a list elist in C-sharp is similar to an array in a sense that it's a data
structure
for storing a number of objects of the same type.
But we use a list when we don't know ahead of time how many objects we're going to store in
that list
to create a list.
We use the list type list is a generic type.
And that's indicated by the angle brackets.
As we see in this example inside the angle brackets we specify a generic prompter and that
parameter
specifies the type of the list.
So in this case I'm creating a list of integers.
We can create a list of anything we can create a list of strings or a list of characters or a list
of any non primitive types.
We can create a class called product and create a list of products.
Generics is an advanced topic and for now that's we know for we to know that when we are
working
with a generic type we need to specify generic parameters inside the angle brackets.
And the third part of this course C-Sharp advanced.
I'm going to cover generics in more detail if we know ahead of time the objects we would
like to store
in the list.
We can initialize wer list using the object initialization syntax as we see here.
So we put the objects between curly braces during initialization of wer list.
And here are some useful methods that are available in the list class.
I had to add an object to the list add range to either list of objects that can be another list or an
array remove to remove one object from the list remove at which removes the object and the
given index
index of which returns the index of the given object contains.
Which tells us if the list contains the given object or not and count which returns the number
of objects
in the list.
Let's really go over to Visual Studio and see all these methods in action.

I'll write this for we I'm going to show we how to work with lists or more accurately generic
lists
and C-sharp.
So let's create a list.
We use the new operator to initialize an instance of the list class.
Note the angle brackets here in the intellisense that indicates that list is a generic type.
I also know that it's defined in-system that collections that generic if we don't have RRE
sharper
than Intellisense we see is going to be different.
I don't think we're going to see the namespace which means we have to go on the top of the
file and
type using system that collections dot generic.
Once we import the namespace then we can come here and create a list.
We specify a type here.
So let's say we would like to create a list of integers.
That's it we can initialize this list ahead of time using the object initialization syntax.
So I'm going to supply one two three four here.
Now we can add something to this list.
So numbers start at.
I would add another one here.
So this is the difference between a list and an array in an array.
We don't have an Add method and once we create the array the size of the array cannot be
changed but
in a list we can add as many objects as we would like.
We can also use the Add Range method to add more than one object to the list.
So numbers don't add range.
And note that in the intellisense here we see it in wer Mirable of INT What is I enumerable.
Well first of all whenever we see a type that is prefixed with I that is an interface I have
covered
interfaces in detail in the second part of this course.
So for now we want to keep things simple.
I want to give we a quick tip here.
Whenever we see I enumerable in the intellisense sincerer we can use an array or a list there.
Once we understand interfaces in the second part of this course then we'll realize that that
interface
is implemented by different classes like the array or the list which means whenever we see I
enumerable
we can supply an instance of a class that implements enumerable.
Now if all that sounds too complex Don't worry about it.
Again remember my tip.
Whenever we see enumerable we can use an array or a list so that we creates an array here.
New Interrail.
I'm going to specify the size of three and I can use the object initialization syntax to
immediately
initialize history or 8 5 6 7.
Now it's very unlikely that we're going to write code like this in a real world application so
don't
be intimidated by this weird way of initializing a list.
All I want to show we here is the number of possibilities when working with lists.
We don't have to memorize anything.
All I want we to take away here is an idea of what we can do with a list so we can create a list
like here.
We can initialize it ahead of time if we know the objects we want to store there.
We can call the add method to add one object to a list or we can call add range to add another
list
or an array to the list.
Now once we have a list we can.
I tried it using a for each loop so for each bar number in numbers cancel the right line
number.
Let's run the application.
So we got 1 2 3 4 1 5 6 7.
Now let's take a look at the index of method.
So numbers dot indexOf this method as a few different overloads.
The simplest one which is the one that is currently highlighted.
Means we can press an item of type integer here and this method returns the index of that
object in
the list if it exists otherwise it returns minus one.
The second overload of this method takes another parameter called index and that's the
starting point
.
So we can say search or search from index 3 and the third overload of this method specifies
the number
of objects to include in the search.
The first overload is what we would be using most of the time.
So let's see was the index of one going to display on the console.
Let me add a label here.
So index of one.
And I would like to have a concert the right line here to separate it from our for each loop.
So Enochs of one is zero.
But interestingly we have two ones here.
Here's the first one.
And here is the second one.
We have another method called last the index of let's take a look at that one.
So I'm going to duplicate this line and instead use the last index of one let's run the
application
.
So last the next or one is four.
So sometimes we may want to start wer search from the beginning of the list.
In that case we use index of method.
Sometimes we might start wer search from the end of the list when in the real world does that
happen
.
I can't really tell we now because it really depends on the algorithm we're designing.
Now let's take a look at another useful member of the list class count so count numbers dot
count.
So this is a property that returns the number of objects in the list.
Let's run the application.
So currently we have 8 objects in the list.
Now let's take a look at the Remove method.
So numbers does remove I'm going to remove one from the list.
Now let's iterate the list again and look at the result after removing one.
So I'm going to copy this for each block and put that here.
Now let's run the application.
So note that the first one is gone but we still have another one.
What if we wanted to remove all the ones in this list.
So one way to do that is to use the for ish look.
So let's change this example to something like this
.
I tried to list one object at a time.
We'd check if number is 1.
Then very move number.
Once we do that let's copy this for each loop again
and put that here.
Let's run the application
application crashed.
Why be good and unhandled exception.
Me here.
This is an exception or an error that we may see from time to time when we're removing an
object from
a list inside a for each block.
So look at the exception detail here.
It's of type system to an invalid operation exception.
And the message says collection was modified enumeration operation may not execute.
So what this means is in C-sharp we are not allowed to modify our collection inside a for
each loop
.
So inside this 4 ish block we have these numbers that remove which is modified to collection.
So how can we change this program to get the desired result without that exception.
We need to use a normal for loop.
So something like for var Y is zero.
Run this as long as I use less than numbers that count then plus Bloss.
And we move this code here.
Now here we need to change that to numbers of.
Because we don't have a local variable like that for each called number.
Right.
So we need to access the current element in the list using an index numbers of why.
OK let's run an application.
There we go.
So we removed both ones from the list.
And one last method before we finished this lecture.
So let's take a look at the clear method numbers that are clear.
So this method removes all elements from the list.
Now if a display count on the console we're going to get zero.
So I'm going to grab this line here and paste that here.
So look the last count is 0.
So this was an introduction to the kind of things we can do with the list.
I hope we enjoyed this lecture and thank we for watching.

OK this section we'll learn more about C-Sharp race we'll learn that in our array's a fixed size
which
means once we allocate them we cannot change their size.
So if we want to work with a dynamic array we need to use a list now these days.
Ninety nine point nine percent of the time we use lists not a race but we might be working
with a third
party library or a legacy code base.
And we we still have to use arrays.
So remember the syntax I'd prefer for use lists.
I hope we enjoyed the section.
And thank we for watching

A.S. I want to teach we how to work with dates and times and C-sharp.
And as part of this I'm going to introduce we to two new types in darknet day time and time
span.
So let's get started.

OK this video we're going to take a look at how to work with dates and times in C-sharp.
We have a type called day time which is a structure that is defined in system name space so
type date
time and we see the structure icon here and that is defined in the System namespace.
So there are a number of ways to create a data an object.
One way is to use the new operator so they time because new day time and the constructor of
the structure
has multiple overloads.
So look at the first one here.
We can specify year month and day or if we want to be more specific we can go up to hour
minute and
second it has a bunch of different constructors so we got to keep it simple.
2015.
January 1st if we want to get the current date time wer access date time Dot now.
So now is a static property of time structure.
So I'm going to stored in a variable called now.
Or if we just want today's date irrespective of the time we can use date time Dot today.
Now that we have a datum object we can access it's components like year month day minute
hour very easily
.
So here's an example.
Now that hour or now a minute.
So let's put a label next to it
and run the application.
So currently it is 12:40 p.m..
So there are a bunch of properties that we can access.
I'm not going to go through each of them because I don't want to waste wer time.
But we've got the point.
One thing we need to know about data objects and share is that there are immutable which
means once
we create them we cannot change them.
So how do we modify them.
There are a bunch of methods and they all start with ADD.
So now Doug.
And so we can add days hours milliseconds minutes and so on to an existing day time
outright.
So let me show we add days 1.
So this returns tomorrow.
Current time.
What do we want to go back in the past.
We use a negative number.
So yesterday it was now that days minus 1.
Very simple.
And one last thing we need to know what daytime objects and C-Sharp is formatting them to
a string
.
So a data object has a bunch of methods for converting it to a date or time string.
So here are a few examples.
Now not too long date string I'm going to duplicate this line a few times.
There's another one too short date string to a long time string.
And two short time strings.
Let's see the difference.
I'm going to comment on these two lines so we can focus.
Let's run the application.
So note that with the first two we only have a date component and not a time whereas with
the last
two there is just a time component.
And obviously this is the long date.
And here's the short.
Now what if we want to display both date and time.
We use two string methods.
So
two strings.
Let's take a look.
So here is the current day time.
We also have this concept of format specifiers.
So to string method optionally takes an argument and here's where we provide a format
specifier.
So take a look at the intellisense here
what we see on the left side is a format specifier.
And on the right side we see an example of that.
So let's take a look at this one where we display a date with the hash notation.
This is very common in passing in SML or Jason.
So take a look at this one.
So if I want to output my day time to something like that we can use this string as the format
specifier
so I can use y y where a 2 digit year or four Y is for a four digit year.
I can use double M and double D.
Let's run the application.
But here's the result.
We can also add time to it.
So I'll take a look.
Double H colon double M.
So currently it's 12:46 p.m.
There are a bunch of format specifiers and we don't need to memorize them if we want to
look at the
full list so them simply go to Google and search for C-Sharp they time format specifier.
And the first link custom date and time format strings
.
So here we can see various examples of these format specifiers.
Their full list and examples for each of them.

In the last lecture we learned about daytime which represents an exact date and time value.
We also have a type called time span which represents a length of time.
There are a few different ways to create a time span.
The simplest one is to use the new operator so the time span calls new time span.
I know that the constructor has multiple overloads.
In this case I'm going to use the third one which takes hours minutes and seconds.
So let's say one hour two minutes and three seconds.
What if we didn't have a value for minutes and seconds we could just pass zero.
So here's an example
.
One hour zero minutes zero seconds.
The only issue here is when we look at this time span object sometimes it's not quite clear
what do
these zeros represent.
Is it the hours minutes.
It's not quite clear.
So a more reliable way to create the same time span object.
We use two static methods on the time span structure.
So time spent as a bunch of static methods and they all start with from from days from hours
milliseconds
minutes seconds and ticks.
So I can just use from hours and pass on here.
I note that between these two lines.
The second one is more readable.
There is also a third way to create a time span if we have two Daytime objects and we
subtract them
.
The result is a time span.
So something like this
.
So and mine start returns a time span and escapes that time span represents two minutes that's
displayed
on the console
.
So here's the result.
Two minutes and it has a slight millisecond value.
I think it's because of the day time that now.
So at the time that we read this value there was a tiny millisecond component in the current
day time
.
OK.
So this is all about creating time span objects.
Now once we have a time span object we can read its properties very easily.
So each time span has a number of properties that come in pairs.
What do we mean by that.
Look at this time span it has properties like days hours milliseconds minutes seconds and so
on.
But it also has paired properties that start with Total.
So total days total hours milliseconds and so on.
What is the difference.
Let me show we with an example.
So
I'm going to duplicate this line and this time I'm going to display total minutes.
So the minutes property returns the minutes component of wer time span object.
So in this case our time span is here the minute component is two.
So that's what's returned from minutes total minutes converse or time span object to minutes.
So in this case it's going to return one hour which is 60 minutes plus two minutes plus three
seconds
which is a fraction of a minute.
So let's take a look at the result.
So as we see meannesses to rest total minutes is sixty two point three or five.
Next
similar to the daytime object.
The time span is immutable which means once we created we cannot change it.
But it provides a couple of methods to modify its value add and subtract.
Both these methods return a new time span.
So let's take a look at a couple of examples.
So what I'm going to do is this time I called Add method.
Note that this method takes a parameter of type time span.
So here I can create another time span.
I can either use the new operator or I can use one of the static methods.
So let's say time span from minutes.
So I had eight minutes to our original time span.
So it was one hour two minutes and 30 seconds.
So now it's going to be 1 hour 10 minutes and three seconds.
There we go
subtract it's very similar.
So why duplicate this line subtract.
Again this method takes a time span object so let's subtract two minutes from our original
time span
.
And the result should be one hour and three seconds.
There we go one hour and three seconds.
Now one last thing we need to know about time span is conversion to and from strings.
So let's scroll down
if we want to convert the time span to a string we simply called the two string method
.
But note that in this case two string is greyed out.
What does it mean.
That means Konsole the right line by default calls this method on any object we pass to it.
So we don't have to explicitly call it.
But if we're not using in the right line and we need to convert a time span to a string value
simply
call to a string.
How would conversion from a string.
We use the Parse method.
So
time span does parse that takes a strange.
So let's say one hour two minutes and three seconds and then returns a time span object.
In this case we pass this time span object icons on the right line.
And this method automatically applies to string on our time span object.
Let's take a look at the result.
There we go.
So parse one hour two minutes and three seconds.
That's pretty much all we need to know about time span.
I hope we enjoyed this lecture.
And thank we for watching
So in this section we learn about two new types in .net Day time which represents a point in
time and
time span which represents a generation.
We remember both these types are structures that are immutable which means once we set
them we cannot
change them.
So let's say if we create an instance of a time and call one of its methods like add month or an
hour
in all cases these methods return and we instance I hope we enjoyed that section.
And thank we for watching.

In this section we're going to take a closer look at C-Sharp strings.


So I'm going to introduce we to a few new methods.
Industry in class and a new class called string builder.
So let's get started.

Earlier in the course we learn that in C-sharp the string key word maps to the String class in
the
Dot Net framework.
So a string is a class and we also learn that strings are immutable which means once we
create them
we cannot change them.
In this lecture I'm going to cover a bit more details about strings.
I'm going to introduce we to some useful methods to work with strings and then I'm going to
show we
how to convert a string to a number and vice versa.
So I've categorized these methods into different groups in terms of formatting wer string.
We can use to lower to convert all characters to lowercase or we can use two upper four
converting
that to uppercase trim is a useful method which gets rid of the white spaces around a string.
And this is important and when we capture user inputs in web forums or Windows Forms if
we want to
search for a character or a string inside a given string we can use the index of or last index or
method
.
Both these methods have overload and they accept it or a character or a string and then return
an index
of the first or the last occurrence of the given character or a string in wer string
if we want to create a substring from a given string.
We use the substring method.
This method has a couple of overloads.
One that takes start the next and then retrieves all the characters from that point onwards to
the end
of the string.
The utter overload takes a lengthy argument to limit the number of characters to retrieve
if we want to replace a given character or a given substring in wer string.
Or use the replace method.
We have a couple of methods here.
Is not empty and is null or whitespace.
And that's a common way to compare a string against now or empty string or whitespace.
If we want to split a string we can use the splayed method in this example.
I'm splitting a string by an empty character which means if we have a sentence with multiple
words since
there is a empty character between each of these words they will all be split.
And what will be returned from this method is an array of strings each element containing a
word.
It's a very common technique to summarize a long string into a smaller one.
I was sure that in the coding demo
there are times that we get a string representation of a number and we need to convert it to a
numeric
value.
For example in most applications when the user types in a number into a text box we always
get a string
.
Even if that string is a number so we need to manually convert that to a number.
There are a couple of different ways to achieve this.
We can use integer to parse or we can use convert to in 32.
I personally prefer convert to 32 because if the string is now or empty this method returns the
default
value for the integer which is zero.
Whereas instead parse throws an exception.
So it's easier and safer to work with convert to 32.
And finally if we have a number and we would like to convert it to a string we can use that to
string
method on that number we can call this method without any arguments.
Which means we can get a string representation of that number or we can format that number
using a
format string.
So in the third line here C is a format string and that's short for currency.
So I just in the example when we format a number at the currency we get the dollar sign and
every
three digit is separated by coma and by default when we format a number as currency.
It's going to have two decimal point numbers.
If we don't want decimal point we can use C 0 or if we want one decimal point we can see
one.
Here is a list of common format specifiers in C-sharp.
So C for currency D for decimal E for exponential F for fixed point an X for hexadecimal.
All right.
Now let's flip over to Visual Studio and let's see all these concepts in action

Are right let's take a look at some of these useful string methods.
So here I've got a variable full name with my name and I know that there is a whitespace
character at
the end of this string.
So first let's take a look at the tree method.
Trim gets rid of the whitespace at the beginning or at the end of a string.
So cancel the right line.
I'm going to use a format string here.
So two single quotes and I'm going to put a placeholder here.
The reason for that is because I want to enclose my string with single quotes so we can see
the effect
of tree method.
Now let's apply some value here.
So full name that trim.
OK let's run the application.
Note that the whitespace at the end of my name is gone.
So this is very important when we receive input from the user.
Sometimes we need to trimming a string before doing processing on that.
Otherwise if we're going to compare that string with another string comparison is not going to
work
.
All right let's take a look at the two other method.
So I'm going to duplicate this line and change the label to of her.
Note that here we can chain these methods because each of these methods on the string class
return a
new string.
They do not modify the original string.
And that's what I meant by strings being immutable.
So Dot to upper less around application.
There we go.
Now let's say we want to break this string into first name and last name.
How do we do that.
There are a couple of different ways.
One way is to look for the index of this space and based on that split that string into two
parts.
So let's try that first.
So full name dot index of we can supply a character or a string here.
So I'm going to use a whitespace character now based on this index.
We want to split the string so we can declare first name as full name but substring.
Now this method has two overloads.
Look the first one takes only an index which is the starting index.
So it starts from that index and goes to the end of the string.
The second overload here takes a start index and a length that is a number of characters to
include
.
So I'm going to use this overload to take the first name.
What is my starting index at zero.
The beginning of the string.
How many characters do we want up to the index of space.
So that's going to be index and last name.
Now this time I'm going to use the first overload.
So I want to start from index plus 1 all the way to the end of the string.
Let's put these on the console
.
OK.
They go.
So first name Marsh and last name Ramadani.
Now there is an easier way to achieve the same thing and that's using the split method.
So if we'd call split we can supply a character or a string here.
So if I supply a whitespace character here.
Look what we get in the result the return type of this method as a string array.
So I store the result in a variable called names.
So if I hover my mouse over var look it's a string array.
Now I can easily get the first name
as names of 0 and last name.
It's going to be names of one.
Let's run the application.
They go.
We got the exact same result.
So if we're working in scenarios where we want to split strings this method is easier to work
with
.
Otherwise if we have some more complex processing we can use the index of an substring
methods.
Now let's take a look at the replace method.
Let's say we want to replace my name here Marsh with my actual first name which is
Marshlack.
So full name dot replace Marsh with Launchbury again here we can supply a character or a
string.
For example we can say Let me show we another example
we can say replace lowercase o with uppercase O or we can say replace whitespace with
nothing with
an empty character.
And this is exactly the effect of applying the tree method.
OK.
Now the important thing to remember is as I told we before all this method calls return new
strings
.
So the original string is not effective.
So let me get rid of these two lines here and display this
on a console run application.
Look washrag Ramadani.
Now let's take a look at a couple of useful methods to work with empty strings or not.
So in real world applications sometimes when we get input from the user we want to see if
the user
actually put a value there or not.
For example imagine we're building a form and the user is supposed to supply a credit card
number we
want to make sure that the user didn't enter a credit card number.
So how do we validate that.
Let me show we.
So look if string is now are empty.
So this is a static method on the string class and it takes a parameter I can supply null here
and here will display an invalid message.
So what do we think is the output of this program.
We should get the invalid message because wer have passed.
Now that's an argument.
So let's just verify that before we go to the next step.
OK we got the invalid message here.
Now what if I put an empty string.
We should still get the invalid message.
Look it's here.
So far so good.
But what if the user just enters space like this.
Technically this is invalid.
This is not a valid credit card number.
So this is equivalent to a user not providing any numbers at all.
Let's run the application.
Look we no longer see the invalid message here.
So this method was one of the first methods that Microsoft put in my framework.
So to work around this problem what we had to do was trim the string first
and then pass it to is now or empty method.
Let's run the application OK.
We see the invalid message now but this is a little bit tedious and ugly.
That's why in later versions Microsoft introduced a new method is null or whitespace.
No we no longer have to trim.
So if the string is empty or whitespace or not are we going to get the invalid message.
There we go.
And before we finish this lecture Let me show we how to convert numbers to strings and vice
versa.
So let's say we receive a number from the user.
And if we're building web or desktop or mobile applications always these inputs come as a
string.
So we going to convert that to a number.
Let's say we get an input which is the user's age let's say 25.
So we need to convert this string representation of number 25 into an actual number.
There are two ways to do this.
One way is to use the converse class.
This class has a number of methods and they all start with to like two in 32 to 64 to double
the decimal
to date time to char to buy it to bully and so on.
So in this case if we want to convert this SDR to let's say an integer I would use convert to
and 32
now integer is 4 bytes and we only need one byte to store someone's age because no one can
be older
than 200 50 years old.
So then we can change these two
to bite and then we can store the result here
and display it on the console.
Now let's take a look at the other situation.
We have a number we want to convert it to a string.
So let's say we've got it price here and that is twenty nine ninety five dollars.
We want to convert this to a string.
We can use price dot to a string.
So every object in dot net has a two string method.
The reason for that is beyond the scope of this course and that's something that I have
covered in my
C-Sharp intermediate course for now just remember this two string method is available
everywhere.
Now we can call this method without any argument which simply returns a string
representation of this
number.
But I want to format this as currency.
So I supply a format string.
So here in the intellisense Luque capital C is currency and by default it has two digits after
decimal
point.
If we don't want decimal point we can use see 0 or if we want one number after decimal point
we
can use see one.
So let's just convert this to currency and display the result on the console.
OK.
So
there we go.
Twenty nine ninety five and we get the dollar sign.
Now let's get rid of the decimal points.
So I put 0.
So it rounded that $230.
OK.
That brings us to the end of this lecture.
I hope we enjoy it.
And thank we for watching.

OK in this lecture we're going to work on an interesting problem summarizing text we have
seen on a
lot of blogs on our home page.
There is a list of blog posts and below each post.
There is a summary and at the end of the summary we see dot dot dot.
How do we do that.
So let's start by declaring a variable.
This is going to be a really really really really really long text.
And we want to summarize it.
The first thing we want to do here is to check if the length of the sentence is below the
threshold
.
If that's the case we simply display it.
Otherwise we need to summarize it.
So if sentence length is less than 20 just an arbitrary number we simply displayed it.
Otherwise we need to summarize the text.
Now the first thing I want to improve in this goal is to get rid of these 20 as a magic number.
I would like to express it it's a constant so constant integer maximum length.
This way we don't have to spread that 20 all over the code as a magic number and the code is
more expressive
now.
All right.
Now how do we summarize this the poor way of doing that is to use the substring method
like this.
So starting from index 0 and taking maximum length but here's the problem with this.
The problem is we make a cut of a wart as a result of that kind of substring and that's not a
good
thing.
We want the summary to look clean.
So we want to take into account the word boundaries so the algorithm we are going to work
on here is
to count a number of words that roughly fits around 20 characters.
How do we do that.
The first thing we want to do is to break this sentence into words.
So
we use the Split method and we use the whitespace as a separator.
No we're going to have a string array of words.
Note that word is a String array.
Now we can iterate over this sorry for each word.
We count the length of that word.
Add them all together.
If we roughly get around 20 or Exit 20 that's a boundary where we need to cut.
So I'm going to declare a variable here called Total characters straight to 0.
Now we're going to loop over the words.
So as simple for each block for each word.
We need to get its length and we need to add it to total characters so total characters plus
equals
for that length.
And we also need to add one because of the space after that word.
Now if the characters exceeds 20 that's the time to get out of the loop.
So.
So immediately break now one more thing we need here is a list to dynamically store all
these words
that are going to be part of the summary.
So
in summary words it's going to be a list of string.
We'll learn about lists in the section about arrays and lists so a list is a data structure similar
to array where we can store a number of objects of similar type but the size is dynamic.
So now in the loop we need to add the kind word to our list then we do our checking to see if
the total
number of characters exceeds max length and we break.
So once we get out of this for each loop are some of the words list as all the words that need
to go
in the summary what we need to do is to create a string and join all these words using
whitespace.
How do we do that.
The string class has a method called join the first argument is a separator.
So the use of whitespace.
And we can pass our summary words Lescure.
Now this joint method returns are summary string Albany to do is to append dot dot dot at the
end.
And that's going to be summary that's displayed on the console
and run the application
note that we didn't cut off a wart
now in a real world application it would be nice to extract all this logic here into a separate
method
or a separate function so we can reuse in different places.
So what I'm going to do now is create a new method here.
So this is the end of our main method.
We can create another method here and that method has to be static because our main method
is static
.
So in order for us to call that method from the main method we need to declare it as static so
static
the return type of that method should be a string.
Let's call it summerize text.
That takes a parameter of type string it text like that.
And I'm going to move all this logic here.
The only problem is we use the word sentence before.
Now we use text so we can replace 10.
So we need to replace it with resharpen is pretty easy.
Altan enter change all sentence to text.
If we don't have resharpen we need to manually go through each of these and modify them.
Now at the end instead of displaying on the console we need to return it.
So return summary.
And also we need to modify this one here.
So if the text is short enough we don't need to summarize it.
We just return it.
Now resharpen is telling me that we don't need this ELSE block here the else keyword
because it's great
out because if the text is more than max length obviously the rest of this method is going to
execute
.
So we don't need to explicitly use else here so we can clean up the code like that.
I like all of that shift and tab to format it can make this code even cleaner because it's obvious
that
this method is returning a summary text so we don't need to store this result in a variable and
return
it.
We can simply put this expression here.
In other thing we can do here is to have a second parameter here that specifies max length.
So instead of hard coding the number 20 we give this option to the caller of this method to
specify
the max length.
This way we increase re-usability so int max length and we can give we the default value of
20 in case
the caller of this method does not want to set the max length and we get rid of this constant
integer
.
And finally back to our main method
we can create another variable called summary call our summerise takes method and pass that
long sentence
here then displayed on the console.
Let's run the application.
We got the same result.
Now we can go and change the max lengths here.
So let's say a max length is going to be 25.
Let's see what happens.
So we got one more word in the summary.
Again we're not cutting off text in the middle of a word.
All we have a clean reusable method that we can use in different places.
And one last thing I would like to do here to improve the reusability of this method is instead
of declaring
that inside this program I want to put it in a class that I can use in different programs because
in
the real world applications we're not going to write all of our code inside the Program class.
We're going to have different classes for different reasons.
So let's add a new class to this project.
I had class lets call it string utility
and now we go back to program here we select this method which I use in our prayer.
We use controlled w to quickly select a block of text like this.
Is much faster than rolling down the shift and using the down arrow like that.
So control w and we can extend wer selection like that or control shift w.
We can reduce the selection cut Norbeck control and tab with which we know and here drop
it.
And finally we need to make this class public.
As I explained in the beginning of this course we're going to just work with public classes
and public
methods in discourse public is an access modifier.
And I'm going to explain access modifiers in more detail in the second part of this course
called C-Sharp
intermediate and of course we need to make this method public as well.
Otherwise it's not going to be accessible.
Let me show we.
So if we go back to a program and now we need to change to summarize takes two string
utility dot c
see there is nothing there because we didn't declare the method as public.
So a control tab back here at the public here.
Back to the program.
Now if we put it here we see that utility method.
All right.
That brings us to the end of this lecture.
I hope we enjoy it.
And thank we for watching

So earlier in the course we'll learn that the String class is immutable which means once we
create
a string object we cannot change its content.
If we're dealing with situations where we have a lot of string manipulation operations we can
use
a string builder string builder as a class that is defined in the system that takes namespace and
represents
immutable string and makes it really easy and fast to create a string and modified on the fly.
But unlike the String class it's not optimized for searching.
So it doesn't give we methods like Index of last index of contains starts with we know all
these strings
searching operations.
Instead it provides a number of useful methods for manipulating strings like append to add
something
to the end of a string insert to add something at the given index remove to remove something
from the
string replace to replace a character or a string and clear.
Let's flip over to Visual Studio and see stream builder in action

Are right in this we are going to have some fun with the string builder.
So let's create an object of type string builder Let's call it builder district builder.
Know that as I typed News Stream builder resharpen automatically added using system to
text on the top
.
If we don't have the sharper.
Obviously we have to add that namespace werself.
Now let's explore some of the methods of string builder so builder.
We have 3 append methods.
Append append format and append line.
Are going to go through each of them.
Let's take a look at the pan method.
This method has a few different overlooks one that takes bool and other one takes byte one
takes character
one takes character and repeats that and one that takes a character array.
Let's use the one that is currently highlighted here.
So I would like to have this dash character repeated ten times now as displayed on the
console.
So that's what we got.
Now let's have a newline here so we can use appendline length.
And after that we can use append again and display some header.
Let's call it Heller.
We can have another newline.
And finally we can have those dashes again.
Let's run the application.
So see we easily created something like that.
Gneisenau is about creating something that looks good.
It's about manipulation of strings.
Like earlier in the course we had a lecture on the random class and there I showed we how
we can create
a random string like a random password in that lecture.
I showed we how to use a character or a two story wer random characters.
Now that we learn about string builder we can use a stream builder to generate random
sequence of
characters.
Let's look at other methods so we can't say replace all these dashes with the plus side.
Let's look at the result.
They go very easy
or we can call it remove and say start from index zero and remove 10 characters.
Let's see what happens.
So the line on the top is gone.
Or we can use the insert method with insert but need to specify an index so we can pass 0
here to put
something at the beginning of this string.
And as the second argument we can't pass anything we can't create a new string here and use
this overload
here.
Specify a character and account so dash and
antenne we're going to repeat that 10 times.
So basically with that we are going to add a line of those dashes at the beginning of our string
builder
.
Let's look at the result.
There we go.
So we see string builder makes it really easy to modify strings and also it's faster than using a
string
and using its manipulation operations because those stream articulation operations like
replace insert
remove all these methods create a new String object into memory and return that.
Now if we have a large number of stream manipulation operations that extra creation of
strings and
be a little bit costly so we can use a string builder.
And this way wer program is going to be even more efficient.
Also note that when we create a stream builder we can also specify a starting string.
So let's set it to Hello World and then we can do all these other manipulations after.
Let's look at the result.
Now interestingly after all these manipulations the first part of hello world is removed then
only deal
is left and the rest is replaced by some dashes.
So $3 is really easy for manipulating strings.
But what we need to remember here is that with string builder we're not going to get string
searching
methods.
So.
Builder Daut.
See.
These are all about manipulation.
We don't have any methods to search for the index of a character or a string inside that string
builder
.
And one last thing is we can use an indexer
to access individual characters in the string builder.
Just like how we do with a string.
So if I want to display the first character
I just use the next year
and let me add a label here
and run the application.
There we go.
There is character.
And one last thing I want to show we here is actually very interesting look at the signature of
the
append method that returns a string builder.
It's not a void method.
It returns a string builder which means we can chain these append methods altogether and
make our code
cleaner.
So this append method returns our builder with the update of string and then right after that
we can't
call this second apan method.
And again this append line returns the optative string with a newline.
Now we can append the rest to it.
We need to get rid of semicolon here.
Same here same here and chained them together.
This makes the code less noisy and more readable and the same is true for other methods here
like replace
remove insert.
All these return a string builder.
So again I can go here
and chain all these methods
just like that.
So the code is much nicer and much cleaner.
So does pretty much all about string Miller.
I hope we enjoy this lecture and thank we for watching.

OK in this lecture I'm going to introduce we to a very important topic procedural


programming.
So what is this all about.
Well procedural programming is a programming paradigm based on procedure calls.
So by procedure I mean function method routine subroutine.
These are all the same thing.
So far all the code we have written in wer exercises was in the main method but that's not
how we
build real world applications because a real world application includes quite a number of
functionalities
and writing all that code inside the main method is going to be a disaster.
So we need to break down our code into a number of methods or functions each responsible
for one thing
.
And this is what we call procedural programming.
We also have object oriented programming which is another programming paradigm which is
based on objects
.
So instead of thinking in methods and functions we think in objects and that's the topic of the
second
part of discourse.
But for now because we want to take things on a step by step fashion I want to make sure that
we really
understand procedural programming and the best way to understand that is by doing it.
So in this lecture I'm going to show we how I would go about extracting some logic from the
main method
into a separate method.
I'm going to do a couple of examples.
So I wanted to pay full attention.
And once we see how I do it then I want we to go over it.
The code we have written in this section for the exercises and apply this technique if we can
to solve
all the exercises.
That's ok don't worry.
We can look at my solutions and extract methods from the code I have written.
So let's flip over to Visual Studio and see procedural programming in practice.
OK.
This is the solution to one of the exercises we had earlier in this course we asked a user to
type their
name and then we reversed the name using an array.
So currently everything is written in the main method.
How can we extract a method or function from this logic.
The first rule of thumb we should always separate the code that works with the console from
the code
that implements some logic.
So in this example over the first two lines we get the user's name.
Then here we have some business logic which is where we use an array to reverse the name.
And here is where we return the reverse name as a string.
And finally we displayed the result on the console.
So let me put a line break here.
So this last line and the first two lines is all about working with console.
We want to make sure that we separate this logic from the logic that is responsible for
calculating
the reverse of any.
Why.
Because in the real world we have different presentation technologies.
We have disto applications web applications mobile apps and there we don't have console.
So by extracting this logic here that is highlighted in two separate method we can reuse that
method
in any application console is only relevant in console applications.
So let's extract this logic into a separate method.
First we start with the access modifier public.
Then we need to use the static keyword and the reason for that is because we are in the main
method
and Main is the static.
In order for us to call this method from the main method this method should be static as well.
Now we need the return type.
What do we think is the best return type for this method.
Should we return an array or a string.
Well what do we expect here.
We need a string to display on the console.
So the return type is going to be a string.
Now give it a name reverse name.
Make sure wer method names are meaningful.
I should be able to look at wer method name and knew exactly what this method is doing
without looking
at it's code.
No parameters.
Do we need any parameters.
If yes how many of what type.
Well all this method needs is that initial name is viable here.
So all the processing is done on the name variable which is a string.
So
this method should take a string prompter called name and return another string which is the
reverse
version of that name.
Now I simply cut and paste this code here in the last line.
We need to return reversed variable.
Ok and now we can change our main method such that
we call our new method reverse the name and the pastor's name here and display the result.
So look the code is more maintainable now instead of everything being the main method.
We have two methods responsible for one thing the main method is purely responsible for
getting the
input from the user and displaying it and the reverse named method is purely responsible for
reversing
the knee.
Now one more improvement we can do here is this variable here reverse.
I see that as a bit of noise because the name of this method we first name is telling me that
what is
coming out of his method is the reverse name.
So we don't need to store it in a separate variable.
We can't simply get rid of it and return the result straight away.
And this way the method is shorter and easier to understand.
Let's take a look at another example.
OK here's the solution to another exercise in this course.
So we asked the user to continuously enter a number or type quit to X it then from that list of
numbers
we find the unique numbers
and file and display them here.
So what part of this code can we extract into a separate method.
Again remember my rule of thumb we need to separate what is about working with Konsole
from what is
about the logic of wer application.
So in this case this is the core logic getting the list of unique numbers from a list.
So I'm going to extract this into a separate method public static what should be the return type
of
this method.
It should return a list of integers.
Now we give it a name get unique numbers.
Now what should be the parameter list of integer as called numbers.
And now we can cut and paste this year.
So finally we return this unique variable here which is a list of integers
and the main method we can assign is viable to a call to get unique numbers of numbers.
That's one way.
Another way is because this is kind of a noise we can simply call this method inside the for
each block
.
OK so now we have a reusable method that we can use anywhere anytime where we have a
list of numbers
and we want to get the list of unique numbers in that list.
Now it's wer turn.
I want we to go over the exercises in the string section the ones we did just before the lecture
and
extract methods or functions or procedures from wer code.
If we get stuck we can always look at my solutions

So in this section we'll learn more about C-Sharp strengths.


We'll learn that strings are immutable which means once we set them we cannot change them.
So if we're working on a problem that involves a lot of string manipulation it's better to use
the
string builder class.
This class is optimized for string manipulation and does not provide methods for searching
strings in
the next section We'll take a look at working with files and directories and C-sharp.
I hope we enjoy this section.
And thank we for watching

A.S. I'm going to teach we how to work with files and directories in C-sharp.
And as part of this I'm going to introduce we to a few useful classes in Dattner file file info
directory
directory info and path.
So let's get started.

OK in this section I'm going to talk about how to work with files and directories and C-Sharp
in dot
net.
We have a namespace called system that I O and that's where all these classes do work with
files and
directories are located.
There are many classes in this namespace and it's really impossible for me to go through all
of them
.
First of all it's going to take a lot of time and honestly I don't have the knowledge of every
single
one of them.
In fact I don't think there is anyone on this planet who knows every single class in darkness
framework
.
So we will discover classes based on wer needs.
But in this lecture I'm going to introduce we to a few very common classes that we may find
useful
in wer programs.
These classes include file and file info directory and directory info and path.
Let's see the difference between them so file and file info classes.
Both provide methods for creating copying deleting moving and opening files.
They have very similar interfaces.
The only difference is FileInfo provides instance methods where whereas file provides static
methods
.
So why do we need different classes for static or instance methods.
The difference is if we're going to have a small number of operations that say good attributes
about
the file it's more convenient to access the static methods of the file class.
But the problem with this static methods is every time we call it a static methods some
security checking
is done by the operating system to make sure that the current user has access to the file.
So if we're going to have a large number of operations this is going to affect the performance
of wer
application.
So in that case it's more efficient to create a filing for class and access all its instance methods
.
This way security check in is done only once during creation of a file object.
So here is a list of methods that are pretty useful to know about these classes.
Again this is not a complete list by any means.
My intention is to just give we an idea of what we can do with these classes.
So create Mithu is of course used to create a file.
We also have copy delete exists to check if a file exists.
Get the attributes which returns the attributes of the given file or move to move the file
around or
read all text which reads all the text in a file directory and directory info are very similar to
file
and file info so directory class provide static methods whereas directory info provides
instance methods
and we use either of these classes to work with directories.
Here are some useful methods.
Create directory delete exists.
Get current directory which returns where the application is currently sitting.
Get files which returns the files in wer directory and in that method we can provide filters.
For example we can say Give me all files or files with a JPT extension.
We also have move and get logical drives which returns the logical drives of wer hard disk
like C drive
D drive and so on.
We also have the path class which provides methods to work with a string that contains a file
or directory
path information.
And here are some useful methods of the path class directory name get filename good
extension which
is very useful.
Let's say we have a path and we want to get only the extension of that path so we don't want
to processor's
string werself.
We just want to get the extension.
So we simply call path God get extension and provide wer string there.
We also have a temp path which returns the path of the current users temporary folder in the
next few
lectures.
We're going to see demos of these classes in action

OK this video I'm going to show we how to work with file and filing for classes.
These classes are very similar and they both provide methods to work that files.
The only difference is file provides static methods where as file info provides instance
methods.
So let's take a look at file look here are the static methods of the file class.
We can copy a file create a file decrypt an encrypted file deleted encrypted check if it exists
and
see there are lots of methods here.
It's really impossible for me to go through all of these methods.
I'm just going to show we a few of them in this lecture.
So we will have an idea of how to use them then we can go and use the other methods
depending on wer
needs.
So let's take a look at copy.
This method takes two parameters.
They both are a string.
The first one is the source filename.
So let's say we would like to copy a file that is located in the C-Drive in the folder temp and
it's
called my file that JPT.
And the second parameter is the destination file it read the tooltip.
It says this cannot be a directory or an existing file.
So let's say we would like to copy these to the drive in the same folder and call it my file that
JPT
.
This method has two overloads.
The second overload takes a parameter of type Boolean which we can use to indicate that if
the file
exists or we can override it.
Now first thing I want to do here to clean up this code is get rid of all these double
backslashes.
So that's where we can use a verbatim string.
They seem to put an answer on here and get rid of all these noisy backslashes
.
That's it.
Let's take a look at the delete method.
Again this method takes a path.
So what I'm going to do I'm going to declare a variable here called pathic so we can reuse it
in different
methods
.
Just like that we can check if a file exists on a disk.
So if the file that exists this method again takes a pass and returns a boolean
then we can do something about it.
And finally if we want to read all the text in a file we can use file but read all text.
This method returns a string or if we want to read a file as binary we can call read all bytes
which
returns a byte all.
So let's try this one again this method takes a path and returns a string.
So we call it content.
Now let's take a look at the equivalent methods in the filing for class.
So we the file info.
First we need to create an object.
And of course we need to specify a path here
and then if we want to copy this file we can call copy to method and this method takes a
parameter
of type string called destination file name.
Again we can apply whatever here.
I know that this method also has an overload which takes a second parameter called bool
overwrite.
Similar to the other method.
I'm going to leave it for now.
Or if we want to delineate finding info that delete takes no parameters to check if the file
exists
.
Filing folder exists which in this case is not a method it's a property.
So if file info that exists then can do something about it.
And finally note that filing for does not have a read all text method.
It's only available as a static method in the file class with the file info.
We need to call the open read which returns a file stream but the stream is a different way of
reading
a file.
And personally I'm not a fan of that because it's just a little bit complex.
Later in the section I will show we a very simple way to read the file.
If we don't want to use file that read all text but the bottom line here is note that both these
classes
are very similar in terms of usage.
The only difference is by providing static methods where as info provides instance methods.
So if we want to execute a small number of operations against a specific file it's more
convenient
to use these static methods so we're going to have to create a new file in file object.
But with this static method every time we call them the operating system does some security
checking
and that can affect the performance of re-application.
If we have a large number of operations in that case it's more efficient to create a filing for
object
and call the instance methods on that object.
That's it for this lecture.
I hope we enjoy it and thank we for watching.
OK in this video I'm going to show we how to work with directory and directory info classes
again to
keep it practical.
I'm only going to demonstrate a few of common and useful methods in these classes so we
get an idea
of how to use this classes.
Then I will point we to the MSD and documentation so we can look at the other methods
available in
these classes.
In case we need to know about them.
So similar to file and file info directory and directory info provide static and instance
methods.
Let's take a look at directory so directory that create directory and this method takes a path so
we
can use a verbatim string here.
Say C-Drive in Tampa folder one as easy as that if we want to get the files in a given
directory we
use directory that get files.
This method has three overloads.
The first one takes a path.
The second one takes a path and a search pattern so we can filter and say give me all the files
with
the JP G extension and the third overload of this method takes a parameter of type search
option which
is an enumeration.
So as an example C-Drive projects C-Sharp fundamentals.
Let's take a look at all files.
So that's my search pattern.
And now I'm going to use search option that all directories.
So this method returns all files in the current directory and it's up directories.
Let me show we the return type of this method to remove the practices and open it again.
Look at the return value as a string array.
So we can use a For Each loop to iterate over the.
So I can store the results in a variable called files
and then do it for each
and display the result on the console.
Let's run the application.
So we see it's returning all files in every directory and every subdirectory starting from C
drive
projects to our fundamentals.
It can change the filter here to say show me only s l n which is visual studio solution files but
take
a look.
So we see I've got a small number of solutions here.
Now let me show we another example.
This time I'm going to call get directory's.
So it returns only the directories inside this path here.
So projects C-Sharp fundamentals
and specify search options that all directories.
So we get all directories recursively.
Now this use a for each loop here.
And this platers off on the console
.
I'm going to comment on these few lines so we can see the difference.
So note that now it's returning only to directories
if we want to see if a directory exist or not.
We simply call directory thought exists and here we specify the path.
So we see all these methods are pretty simple and we don't need me to go through each of
them and
waste wer time.
We can learn about them werself.
The only thing I want to show we in this lecture is the difference between directory and
directories
for using Xacto like file and filing for.
So I'm going to show we one example.
I create a new directory info specify a path here whatever.
And now if I want to get all files or all directories inside this directory object simply directory
info that get files or get directories.
So this method is exactly like the other method.
It takes a search pattern on an enumeration called search option.
Now that's pretty much all I wanted to show we about directory and directory info.
If we want to learn about individual methods in the file file in full directory and directory in
for
classes simply go to Google and search for say file info class C-Sharp then pretty much in all
cases
.
The very first link and Google is the documentation for that class on MSD n Microsoft
Developer Network
.
So let's go here.
So here is the official documentation of filing for class.
Can scroll down and look at each of these properties and their description.
Same for the methods all here with their description.
Let's take a look at one of them here.
Let's say encrypt.
Now scroll down here and look.
There is already an example for we here.
So it's not rocket science.
We can easily figure it out on wer own.
I hope we enjoy this lecture and thank we for watching

It is when we are going to take a look at the path class.


This class provides a number of methods that makes it really easy to work with a string that
represents
a path and extract different parts of that path.
So we don't have to do the string processing or itself.
So here is an example.
Imagine we have a path like what we see here if we want to extract only the extension here
and sell
in the poor way of doing that used to use the string class
and search for index of say Dot.
And that would return the dog team next.
Right.
And then I can say past a substring from that dot index that would return the extension.
So we don't want to do at these low level string processing ourself.
And that's when we use the past class.
So with the path we can say get extension now that this is a static method we can't provide
our past
variable here and to simply display the result on the console.
Let me add a label before it
and on the application look good returned Dot sln.
Or we can use get filename to only extract the file name in that path.
So filename plus path that get file name it also has another method called Get filename
without extension
.
So last time we'd find them without extension we change the label.
And another useful method is get directory name.
So I change the label here.
Get directory name.
Let's take a look at the result.
So not that good filename on the return the filename with extension if called Get filename
without extension
this is what we get.
And if we call it directory name it returns the directory in which that file is sitting.
So this class makes it really easy to work with a string that represents a path.
In case we need to use this class in wer program I encourage we to look at the MSD
documentation
to have an idea of all the methods that are available there so we don't have to reinvent the
wheel
.
That's it for this lecture and I'll see we in the next lecture.

So in a fiction we learned about different classes in .net to work with files and directories.
These classes come in pairs like file and file info files per wise static methods.
Whereas filing for provides instance methods which one do we use depends on the number of
operations
.
If we have small number of operations it's easier to use the File class because we don't have
to create
a new object.
But remember every time we access a file there is some security checking done by the
operating system
.
And if we have a large number of operations it's going to be costly.
So it's more efficient to use the file info class.
In those cases and the same applies to directory and directory.
And remember if we need to access individual parts of a path like the extension filename
directory
name it's easier to use the path class as opposed to string searching methods in the String
class.
I hope we enjoyed this section and I will see we in the

A.S. I'm going to show we a few techniques to debug wer applications I'm going to show we
how to
use breakpoints watchers Carlstadt locals and those windows.
I'm also going to talk about some good programming practices such as defensive
programming.
So let's get started.

This with video I'm going to teach we how to debug applications.


So I've written a small program that displays the smallest numbers in the list.
So as we see it on the first line we define a list or integers with numbers from 1 to 6.
Then we call this method get smallest we pass our numbers list here and three here means
return three
smallest numbers in this list.
And finally we iterate over this smallest list and display them on the console.
So before we get a closer look at the code let's run the application and see what's wrong here.
So with control on at 5.
So instead of getting numbers 1 2 3 regaining 6 5 4.
So this is not the list of smallest numbers.
Let's see what's happening here.
So we have two methods get smallest and get smallest.
Let's expand this method.
So in this method first we define a list to hold the smallest numbers.
Then as long as the number of elements or the number of objects in this list is less than the
count
that we pass to this method we're going to run this logic.
And here we make a call to get smallest method passing the list and we expect this method to
return
the minimum number in that list.
Next we add this minimum number to our ultimate list of smallest numbers and remove it
from the original
list.
So this way the first time this why loop is executed.
We should get the list of 1 to 6.
So I expect one to be returned and added to the smallest list and removed from the original
list then
repeat with this list 2 to 6 and then repeat this as long as we have less elements in this list
than
the count that this method receives as an argument.
Now let's take a look at Get smallest method.
So here first we assume the first element in the list is the smallest number.
Then we start iterating over the list starting from index one up to number of elements in this
list
.
And for the current number if it's greater than the minimum we change the minimum.
So if we're experience we know that here we have a bug but if we didn't catch it that's
perfectly
fine.
That's the purpose of this video.
I'm going to teach we how to use debugging in Visual Studio to find bugs in wer program.
So how does debugging work in terms of the process.
First we need to put one or more breakpoints in wer application and then run wer application
in the
debug mode.
When we run wer application into debug mode the execution stops on wer breakpoint and
there we can't
inspect the values of different variables to make sure they're holding the right value.
And if not we can change wer code.
So I'm going to put a breakpoint at the beginning of the main method here.
We can put a breakpoint by pressing f 9 or we can remove it by pressing f 9 again.
I know we run the application into debug mode.
How do we do that.
EF 5.
So remember this shortcut.
EF 5 is run in the debug mode where as control f 5 is run without debug.
So I'm going to press 5 now.
So look the program started and execution stopped at the line where I put a breakpoint.
Now at this point I can look at the values of different variables or I can continue execution.
There are a few different ways to continue execution.
One common way is what we call step over and a shortcut for that is 10.
So if I press F 10 Now this line is execute it.
So we left then we execute one line at a time.
Now I'm going to press on one more time and hover my mouse over smallest viable.
Let's inspect this.
So we have 6 5 4.
So this is telling me that there is something wrong in this method.
Get smallest.
So let's go back.
Look at this yellow arrow here.
I'm going to track this and put it back here.
I press tend to step over one more time but this time I'm going to step into this method
because I want
to know what is happening here and to step into.
We use F 11.
So remember the shortcut f 10 is a step over and if 11 is step into
now we press turn again.
So first where do we find a new list.
That's fine.
If 10 again now at the beginning of the while loop if 10 again and again.
Now I can save my time by pressing another breakpoint here.
So next time I run the application into debug mode I don't have to do all these 10 if 10 if 11.
I can just jump here straightaway.
So f 9 for another breakpoint.
Now we saved my time.
I don't want to jump into this message straight away because maybe this method is doing its
job properly
.
So first I'm going to step over it.
So I have 10.
Now let's take a look at men.
So what is coming out of this method is number six.
And what was the input list with numbers 1 2 6.
So this is telling me something is definitely wrong inside this method.
So let's go back and this time I'm going to step into it and for 11 now have 10.
Now I'm going to introduce we to a very useful tool when debugging wer applications.
The watch window.
So we can open it via debug windows watch watch one.
So what is this window.
We can't put the variables that are of interest to us in this window.
And this way we can look at their values at all time.
Then we don't have to hover our mouse over them one by one.
It's much easier now.
Look at the code here.
There are a few variables that are involved in this algorithm.
One is men and other one is list of zero.
And the last one is LISTO.
So I can put these variables in the watch window and look at their values at all time.
So here in the watch window men list of zero and list of I now note that list of AI is not
defined yet
because AI is defined in a four block.
And currently we are outside the four block.
So we step over this line with FTN.
Now look at the watch window.
Note that the value of men is indicated as red.
Red means the value just changed.
So now mean is one let's continue execution by 10 10 10 10.
Now look at the value of list of eye in the watch window.
So the current value in the list is 2 and we're comparing this with men.
We are seeing if listo eye is greater than men said men to list of eye.
So with this logic we're constantly looking for a larger number.
And this will return the maximum number in the list not the minimum.
So this is where the problem resides I can easily fix this by changing this condition to Lester
now
enlisted over 8 10.
So did we notice that this line was not executed.
So the value of men was not changed and as we've seen the watch window is still one.
So it appears the problem is solved.
Now I can continue stepping over different lines here.
But I think we'll get lost in the detail.
Let's step out of this method and quickly look at the end result.
How do we step out which shift and if 11.
So let's repeat the shortcuts for 10 to step over a line if 11 to step into 8 and shift and if 11 to
step out of a method.
So now I press shift that F 11.
Look we are back in get smallest method.
Now I can step over this line and look at the value of Min.
So I have 10.
I think the problem is solved.
Look at the list.
So our list is numbers 1 to 6 and Main is 1.
So let's stop the debugger and run the application in the normal mode without debugging and
see if we
get the right result on the console.
How do we stop debugger red shift and if 5 again to review at 5 to run the application in
debug mode
and shift and 5 to stop the debug mode.
And now I'm going to run the application without debugging with control and F5.
Awesome.
We fixed the bug.
Well wait a second here.
We're not done yet.
This program has a few more bugs that we haven't seen yet.
And that's what we're going to cover over the next few lectures.
So we're going to review these debugging techniques and along the way also show we other
tools to fix
the remaining bugs in this program.

One thing that distinguishes a good programmer from an average one is that a good
programmer often thinks
of cases.
What they mean when each case is uncommon scenarios an average programmer often
assumes the end user
enters values into the forms the way the programmer expects but the reality is different.
So back in the example from The Last Lecture look at the first line here we have a list of six
numbers
and in the second line we want to get the three smallest numbers in this list.
What if we only have 2 numbers in our list.
So I'm going to remove these four numbers and run the application
the application blew up we got an exception.
So close the program we got argument out of range exception and Index was out of range.
So what's going on here.
When we face situations like this that's when we start debugging.
So I want to run the application into debug mode and find where in the code we're getting this
exception
what line.
So remember our shortcut and five to run application in the debug mode control at 5 to run
the application
without debug mode.
So I press 5 now.
OK we start at this break point.
I want to continue execution.
So in the last lecture we learned about step over step into and step out there is one more way
to continue
execution.
And that is continue to build the next breakpoint.
So I can press F5 again.
A look now we are at our second breakpoint.
So so far everything seems to be fine.
We didn't get an exception.
So let's continue.
If I have one more time.
OK we're back on this line again one more time.
Mm hmm.
I don't seem to be right.
We know what I want to get rid of all these breakpoints and just run the application and see
where
exactly blows up.
So this is something that often comes up when we're building big applications.
We put various breakpoints here and there and once we fix the bugs we forget to remove
them.
And then these break points getting the way.
So how do we find them and how do we remove them.
We go to debug.
One way is to go straight here and click delete all breakpoints or disable all break points.
That's the quick way.
There is also another way we can go to Windows
and breakpoints.
So here we see all the breakpoints in the application what file what line what character can
DoubleClick
go there.
We can disable them or enable them or we can delete them.
So I'm going to delete both of these.
Now I want to restrict application.
The shortcut is control shift and F5.
If we ever forget these shortcuts we can always find them.
Just go to the Debug menu here.
So look we've got continue which is a five step debugging which is shift and a five.
I know I'm looking for restart which is control shift and F5 so restart application.
OK this is where it blew up.
So I put a breakpoint here as my starting point f nine.
Now let's look at the exception argument.
Out-of-range.
So what's happening.
Let's close this.
Look at this list.
This list is empty.
There are no elements here yet.
We are assuming mean is the first element in the list.
So this code is not really reliable and this is one of those areas that separates an average
programmer
from a good programmer.
Now before we fix this bug Let's see why is this less empty.
If we remember this line the purpose of this was to remove the smallest number from the list
and we
continue repeating these until we get enough small numbers based on the value of count here.
So as we're removing these numbers from the list at some point the list becomes empty.
In this case because our list originally had 2 numbers in it after two eiter patients the list
became
empty.
And that's why we get this exception.
Now the question is how do we fix this but we have a few different ways here.
One way is to have an IF block in the Gets smallest method that checks if the count that we
pass here
is greater than the number of elements in the list.
The reason we're getting this exception is in this case we want three small numbers.
What the list is only 2.
So this is one way to solve this problem.
Another way is to put it conditional in get smallest method.
So we need to check that if the list is empty.
So if the list is empty what should we do.
Should we return 0.
I don't think so.
Imagine if our original list.
I mean this list here had a number of negative numbers that at some point we get here the list
is empty
.
And Bridger's zero.
So the program end up displaying zero as one of the smallest numbers in the list which did
not exist
in the list in the first place.
Another option is to check if the list is empty here.
Throw one exception.
So that's one of the conditions or criteria for this method to do its job.
This is what we call defensive programming.
So when we get input here before doing any processing we want to make sure that the input
satisfies
some criteria.
If not we are not going to continue processing.
Now there is a third way here.
Can we see that.
It's not quite obvious but yet is very important.
Look at this method get smallest.
This method has a side effect.
So this original list that was sent here we are continuously removing some numbers from it in
order
to calculate the smallest numbers and side effects are not good.
They make wer methods unreliable and they're often hard to find bugs that are because of
side effects
.
Now for a second I want to stop the debugger here.
I'm going to put those four numbers back here.
So if we're on the application now everything works OK.
We got one two three but let's iterate over the original list.
So I'm going to change these two numbers.
Look at the result.
Our original list is changed one to three is removed there.
And this is what I meant by side effect.
So in my opinion that's a more serious problem that we need to address first.
Now that may or may not solve the bug that I introduce at the beginning of this lecture that's
fine
.
If it doesn't fix it we're going to continue debugging and find a right way to fix that bug.
So the first thing I want to do here is to remove the side effect.
How do we do that.
So in the good smallest method instead of removing these numbers from the original list I
want to create
a copy of this list to do my processing.
So
I call this less buffer so we create a new list and pass that original list here and then instead of
removing these numbers from the original list I remove them from the buffer.
And one more change here we need to change this list to buffer.
So now look this list the original list is only used during the creation of the buffer.
Now let's run the application
OK.
Beautiful.
The original list is not a.
So we removed the side effect.
Now let's get back to the original bug that I introduced at the beginning of this lecture.
So I'm going to remove
these four numbers and change the foreach block to look at the smallest numbers.
Let's run application.
OK we still have a problem here.
So in the next lecture I'm going to show we how to fix this problem.

OK back here we want to fix the book from The Last Lecture.
So we have a list of two numbers and we want to get three the smallest numbers in this list.
And as we remember from the debugging session in the last lecture this problem happened.
And this line here.
So at some point the input list that we give to this method becomes empty and we try to find
the minimum
number in an empty list.
Well we have two choices to fix this problem.
We can put a conditional statement here and make sure the list is not empty.
That's one way the other way is to have a conditional statement.
In this method here.
So we want to make sure that count that we get here is not greater than the number of
elements in this
list.
Now both these solutions might sound reasonable but which one do we think is a better
solution.
I think a better solution at this point is to check if count is not greater than the number of
elements
in this list.
Why.
Because we're asking a question in this method.
But the question itself has a problem.
If the question is meaningless we can not get an answer.
Let me use a metaphor.
Imagine we ask wer friend.
Do we eat with a pen and paper doesn't make sense.
The question should be do we eat with a spoon or fork or with chopsticks.
So when the question is meaningless we cannot provide an answer.
So in this case I'm going to attack this problem by making sure this method gets smallest gets
the right
arguments as the question.
Now
so I'm checking if count is greater than the number of elements in this list.
Then we throw an exception exception of type argument out of range exception.
This is a useful technique in defensive programming so we check the input first before doing
any processing
.
Now one more thing I would like to add here we can have a message here.
Count cannot be greater than the number of elements in the list.
Let's run the application now.
The application crashed again.
So have to solve the problem.
Yes we did solve a part of the problem.
Now we might ask Marsh how is this better than before because before we got an exception
anyway.
Let's see the difference re the exception argument out of range exception count cannot be
greater than
the number of elements in the list.
So this exception is more meaningful is telling me why the program crashed so when it
comes to troubleshooting
I would have a better idea of what's happening here.
I would know that the client of this method in this case this line here is sending the wrong
data.
Let me temporarily comment out these two lines here and run the application again.
Read the error now index was out of range.
Must be non-negative and less than the size of the collection.
This error message is too low level and is coming up from a method.
Further down in the list of method calls so it came from this method here.
The important thing to consider here is we should not get here in the first place.
The program should stop execution at this point and that's why we added this.
If block.
Here the reason I add this here is not just to display a more meaningful message is to prevent
wer
application from going in the wrong state.
Now this is a very simple program but imagine if this was a big real world application with a
database
.
If wer application goes in the wrong state there is a chance that sometimes that state is
persisted
in the database and the next time we load a page we show some data to the user that makes no
sense
and in situations like that we're going to have a hard day finding that bug.
We can spend a day or two maybe even a week to figure out what was happening.
OK back to the business here.
Now we solve this problem with this count being greater than the number of elements in the
list.
What do we count as 0.
Do we think it's a valid question.
Give me zero smallest numbers.
No it's a ridiculous question.
What if it was minus one.
It just doesn't make sense.
So we need to change this slightly to something like.
So if count is greater than the number of elements in the list or is smaller than or equal to
zero.
That's out of range.
Of course we need to change this message slightly
.
Counts should be between 1 and the number of elements in the list.
Let's run the application.
OK we got this meaningful exception here because we passed minus one to this method.
Now to further expand this topic of defensive programming.
What if we send an empty list here.
Something like this.
We might say OK Marsh we can do another check here to make sure that the list is not
empty.
We can certainly do that but in this case I can show we that the existing logic would work for
an empty
list.
Why.
Because first of all I know we cannot send minus 1 or 0 here so we need to send one and
because one
is greater than the number of elements in the list.
This logic will stop the program execution so there is no need to write.
If list that count is 0.
Throw an exception is just redundant.
But what if the list was null.
What if I send null here then I'm going to get another low level exception.
Further down the track.
So let's investigate that run application.
The famous null reference exception object reference not set to an instance of an object.
So this is something that I would like to prevent.
At the beginning of this method to make sure the question is the right question
.
So if list is null we throw an argument not exception.
OK so in this lecture we covered some of the cases around this algorithm and we improved
the reliability
of our code.
And that brings us to the end of this lecture over the next couple of lectures.
I'm going to show we more debugging tools in Visual Studio.
I hope we enjoyed this lecture and thank we for watching.

OK back here I changed the declaration of our list back to what it used to be.
So numbers 1 2 6 and also added.
Number three here.
So we get three smallest numbers in this list.
Note that we have one breakpoint here.
Now I'm going to run the application in the debug mode.
So 5 so we are here.
Now this is a very simple application with only three methods but often a real world
application consists
of tens hundreds or even thousands of classes with a few methods.
So sometimes when we're debugging we might get lost.
Now I'm going to introduce we to a window that shows we how we got here.
This window is called call stack so we can find it in debug windows call stack.
So this window shows the order of methods that were called from the moment that the
application ran
up to where we are now the item on top of this list is wer current location and the item on the
bottom
of this list is where we started.
So we can double click here.
That brings me here.
Let me dock this window.
I don't like this one.
So before we jumped into this method this is where we were.
Now I double click main and this is how we started.
So we went to this method and then ended up here.
And finally in get smallest method.
So if we get lost.
Remember the call stack window

Add one more thing.


So earlier I told we about the watch window so we can bring it from de-bug windows watch
watch one
now watch we know it's useful but sometimes it may get a bit tedious to type the name of
variables we
would like to inspect.
So I'm going to show we two more windows that are useful in debugging auto's and local's
we can find
both of them under debug windows auto's and locals.
So let me bring it up here.
So the altar's window is like a watch but with automatic list of variables visual studio based
on where
we are in the code detects the variables that we could be interested in.
So here we see it has less to I which is the loop's counter variable.
We have the least viable mushes to put it into this method list or count because we have
references
here in the code list of I.
Because we're using it here and men again we have reference them here.
So this saves we time the locals window is similar to the auto's window.
So the difference is it does not list all kind of variations that we see in the autos we know.
For example here we have on the lists I mean whereas in Antos We also had list or count and
LISTO.
So the locals window shows the variables in the local scope.
So depending on wer preferences we might use low calls auto's or to watch window.
I hope we enjoyed this lecture and thank we for watching.

In the section we learned about debugging tools and visuals to we.


So here's the process.
We put one or more breakpoints in wer code and then run the application in debug mode.
Next we continue execution and inspect values of different variables of watches we.
Remember wer shortcuts have five to run the application in debug mode.
If 10 to step over a line f 11 to step into a method shift and if ever to step out of it and shift
and
5 to stop the debugger.

WHATS NEXT
So we made it this far.
I hope we have enjoyed this course.
Now this course is the first part of my three part C-Sharp course over the next part which is
called
C-Sharp intermediating.
We'll take a closer look at C-Sharp classes.
I'm also going to talk about a very important topic that a lot of C-Sharp developers struggle
with and
that is called interface's.
I'm also going to introduce we to object oriented programming.
I'm going to talk about encapsulation inheritance and polymorphism.
So I hope to see we in the next course.
And remember we can find coupons for my other courses at the end of this course.
So have a great day and I hope to see a

INTERMEDIATE

 C# Intermediate: Classes, Interfaces and Object-oriented


Programming

No that object orientation is a complex topic and it takes a lot of books videos and years of
thinking
to really -- but this course opens wer eyes to the object orientation.
We learn the principles of object orientation including encapsulation inheritance and
polymorphism
.
I will show we why encapsulation is so important and how it helps writing robust code.
I'll talk about inheritance inheritance is a way to reuse code but unfortunately it's misused a
lot
by a lot of amateur designers and developers.
I will show we the problems with inheritance and then I'll introduce we to the concept of
composition
as a more flexible way to reuse code.
Then all talk about polymorphism.
I will show we how we can take a piece of code that has a lot of if else and switch statements
and
refactoring it into an object oriented style.
We learn how we can change the behavior of an application by extending it.
So instead of changing the existing code which may affect parts of wer application we create
new classes
that change the behavior of wer application.
And this is extremely powerful.
And finally I'll talk about interfaces.
Unfortunately there is a lot of wrong information about interfaces in the community.
In fact when I started learning C-Sharp back in 2002 the book I read which was actually
published by
Microsoft gave me the wrong information about interfaces.
And for that reason I was confused about interfaces.
For years I was taught that interfaces are used to implement multiple inheritance in C-sharp
and that
is absolutely wrong.
It took me years to really understand interfaces and that's the reason I decided to create this
course
for we.
So whether we're brand new to the concept of classes interfaces and object oriented
programming or
we have some experience we're going to get a lot out of this course.
I will show we how it interfaces improve the testability and extensibility of wer application
so we'll
see an introduction to unit testing and how we can use interfaces to improve the testability of
our
application.
I've been really excited about making this course and I hope we'll become a better developer
after
watching this course.
That's enough introduction for now.
Let's get started.

OK we're going to start our journey by learning about classes.


In this lecture I'm going to introduce we to the basics of classes.
I'm going to show we a real world example of classes and why we need them.
Then I'm going to talk about what is an object and how it's different from a class.
And finally we'll talk about static members.
So what is a class.
A class is simply a building block of a software application.
So in the real world an application consist of multiple classes each responsible for a particular
behavior
in the application and overall all these classes together will provide the behavior expected
from the
application.
Let's take a look at a real world example.
We all are familiar with the concept of blogs and posts.
Let's say we would like to implement a web application as a blog engine with a typical
layered architecture
or our application consists of at least three layers.
Presentation business logic which is also referred to as domain layer and data access which is
also
referred to as persistence layer.
In each of these layers we can have classes each responsible for something particular.
For example in the presentation layer we can have a class like post view which is purely
responsible
for displaying imposed to the user in the business logic or domain layer.
We can have the concept of post itself.
And finally in the data access or persistence layer we can have a class like post repository
which knows
how to save opposed to the database or loading from a database.
A real world application often consist of hundreds or even thousands of classes collaborating
with a
shudder.
So for we as a C-sharp programmer it's absolutely crucial to understand classes and how to
use them
effectively to build a maintainable clean robust reliable application.
This lecture is pretty basic but as we progress in this course in every lecture and in every
section
I teach we something new about classes.
By the end of this course we're going to learn a lot of materials about how to use classes and
interfaces
to be loosely coupled extensible and maintainable applications.
So let's continue our journey.
Now we know a little bit about the class.
So it's a type that we developers define and give it a responsibility depending on the kind of
application
we are building and the layer that class belongs to what is inside the class.
The class essentially has two parts data which is represented by fields and behavior which is
represented
by methods or functions.
Here is how we illustrate a class in UML or unified modeling language.
UML is a graphical language are representing classes under collaboration and we use that as
a communication
tool as part of building sulfur.
So in UML a class has three parts the first part is the name of the class.
Then here are the fields or attributes of that class which represent data about that class.
And finally we've got the methods or functions which provide some behavior.
So in this example our Person class has feels like Name age height and weight and it has
methods like
walk talk eat and sleep.
Let's take a look at another example we talked about blogs and posts.
So a blog post can have attributes or feels like title description and date time and it can have
methods
like Publish like or comment which receives a message a term that is often used with classes
and sometimes
used interchangeably is an object but an object is fundamentally different from a class.
Yet a lot of developers including myself sometimes use the word object to refer to a class but
an object
is essentially an instance of a class that resides in the memory.
So back to our personal example.
If person is a class we can have objects like John Mary and Scott.
These are instances of that person.
The person class or the person type defines the blueprint from which we can create objects at
runtime
.
These objects into memory talk to each other and as a result we get the behavior expected
from the application
.
Now let's see how we can declare a class in C-sharp.
Here's a basic syntax for declaring a class public and class or keywords or reserved keywords
in C-sharp
.
And that's why I've indicated them with blue polling is what we call an access modifier and
that's something
we're going to learn later in this section.
So for now don't worry about it.
Each class should have a name or an identifier like person.
In terms of naming convention in C-sharp use possible case name or classes.
What is Pasko case in Pasko case the first letter of every word should be upper case.
We also have camel case in which the first letter of the first word should be lowercase but the
first
letter of every word after that should be uppercase in SUCIA.
We use camel case when naming parameters of methods as we will see later in the section.
So back to the declaration of our class the class can have fields and methods which we refer
to as members
of that class.
It put members inside this curly braces here we can declare a field for this class and call it
name
similar to the class we start with an access modifier.
In this case public and the data type for that field and an identifier in the real world
applications
we shouldn't declare fields with public.
This is purely for taking we on a step by step journey without confusing we with a lot of
details
along the way.
As we progress in this section we'll find the best way to declare fields.
OK now let's see how we can declare a method in this class or similar.
So we start with an access modifier.
And here is the signature of the method.
So a method that can have a return type.
In this case void means it doesn't return any value and it has an identifier.
And here in brackets we can't put any prompter's that that method may need inside the
method.
We have the code and here we can access any of the members of that class.
So in this example I'm simply using console dot write line to display the name of that person
on the
console.
OK now that we have a class let's see how we can create an object or an instance from it to do
that
b is the new operator.
So we start with the type of the class.
In this case person we give it an identifier and then we use the new operator along with the
name of
the class to initialize an instance of that class.
Note that here we are using common notation for naming the person object.
A shorter way to write this go is to use var.
Var is a C-sharp keyword.
And the reason we use that used to save us from typing the full name of the class because
sometimes
the name of the class might be quite a few characters.
Plus as we see it's a little bit of duplication.
To repeat the name of the class in two places.
So we use the VAR keyword and the compiler automatically knows that this person object is
of type person
.
Now that we have an object we can access members of that object like accessing the name
field and giving
a value.
Or we can call one of its methods before we start coding.
Let's talk about class members in C-sharp we have two types of class members.
We have instance members and static members and instance member is accessible from an
object we have
already seen that before.
So we create the person object and then call the Introduce method on the object.
But we also have stunning members and static member is accessible from the class not an
object.
An example of that is console that right like a console is a class and right line is a static
method
.
So we don't have to create an instance of console using the new operator in order to call right
line
.
Now we may wonder why do we use a static members.
Basically we use them to represent concepts that are a singleton.
That means we should have only one instance of that concept into memory.
Think of the concept of the current day time we should have only one place in the memory
where we know
the current day time.
It doesn't make sense to have different objects.
It's telling us that current day time is a different value.
Another example is console dot write line when we on a console application.
Basically we have only one console and that's why the console class and all these members
are defined
as static to declare a member as a static.
All we have to do is to use the static keyword for the access modifier.
We can use static on any members of a class.
OK.
That's no theory.
Let's open up Visual Studio and do some coding.
OK here I've got a console application in Visual Studio and that's where we are going to do
all the
coding for this course.
We're not going to get into the complexity of Windows applications or web applications or
mobile apps
.
We just want to learn about classes interfaces and object oriented programming.
What we learn here is we can always apply in any kind of application we're going to build
OK and
start creating our first class.
So we create a class by public class.
Let's give it a name like person
let's define a field for it so public.
String name again for now we're going to use public until we get to the lecture about access
modifiers
and then we're going to learn a better way to define fields and let's create a method called
introduce
.
I want this method to take a parameter and that's the name of the other person that this person
is going
to introduce himself to.
So let's say introduce two and here we use the console class dot write line method.
Hi 0.
I am one.
Basically what we have here is what we call a format string.
So it's like a template.
And here are parameters that we will fill with some values.
So I want the first parameter to be filled by the value of two argument and the second one is
going
to be the name field stored in the class.
Now that we have this glassless create an object from it.
So we go to the main method.
We can either go person person equals new person or a shorter way.
Easy to use for.
So with var we'll let the compiler figure out what is the type of this person object.
Well the compiler knows it's a sign to the new person object here.
So when we hover wer mouse over var we'll see the tooltip says person.
Now we can assign this person name person that name a calls a John.
I then can call the Introduce method and pass another name as an argument say introduce
werself to
Marsh.
Now if we run this application
we see.
Hi Marsh I'm John.
Now let's take that to the next level.
Let's say we would like to create a personal object from a string.
What we can do is to create a parse method.
So let's go and define the Parse method here.
The parse mother should take a string and return a person object.
So person parse straying.
So SDR.
Basically what we need to do here is to create a person object set the name field based on the
SDR argument
here and then return that so far.
Personally a cause new person
with set the name to SDR and finally return that person.
Now the interesting thing here is if we want to use this parse method we would have to use it
on an
object because it's an instance method.
So that means I can go here and say person Daut parse and give it a name like John and that
returns
a person object.
So let's call it P and we can get rid of this name here for now.
See it's a little bit weird.
We have to create the person object first and then call the parse method to return a person
object.
It just doesn't make sense as fair to use a static modifier so we can declare this parse method
as a
static and this way we don't have to create the person object first in order to parse a string so
we
can simply change just go to
use the person class.
We parse that string and now we have a person object.
And finally we can call the Introduce method on it as run the application.
We get the same result.
So that's a use case for using a static member is static member is only accessible from the
class and
not an object.
That's pretty much it for this nature.
In the next lecture we're going to learn about constructors.
I hope we enjoy this lecture and thank we for watching.

OK we got to constructor's what is a constructor.


Constructor is a method that is called when an instance of a class is created.
Why do we need a constructor.
The intention is to put an object in an earlier state that is to initialize some of the fields in the
class.
Here is how we declare a constructor.
So as we see we have a class called customer and this class has a constructor as we see here
the constructor
has the exact same name as the class.
And that's a requirement.
If we change this name the compiler or the runtime will not treat this as a constructor.
Also note that constructors unlike other methods do not have a return type not even void.
Here in this method we can do any kind of initialization that is required.
Note that we don't always have to use a constructor but if we need to initialize an object upon
creation
that's where we put our code.
In this example we have what we call a parameter less or a default constructor.
This constructor has no parameters.
If we don't define a default or parameter list constructor for wer class the C-sharp compiler
creates
one for it.
We're not going to see it but it will be in the L or intermediate language code that will be the
result
of the compilation that constructor doesn't do anything.
It just initializes the fields of the class to their default values.
What are those default values for any kind of numbers.
It sets them to 0 or boolean types and sets them to false for any other kind of reference types
like
strings or any other objects sets them to know and for character sets them to an empty
character.
Here's another example of a constructor.
In this example we have a parameter here.
So we get the name of the customer and we set the name field.
As we see here Note the use of the this keyword.
This is a keyword that references the current object.
Why do we need that here.
Look here we have two identifiers that look very similar.
We have this name field in the class and its name parameter in the constructor of this class.
They both have the same spell but are using different naming conventions.
This parameter here is using camel case.
So the first letter of the first word is Laura case the name field here is using Pascal case.
So the first letter of the first word is uppercase.
It is possible that sometimes we make a mistake and in the assignment operator here we put
the wrong
variable on the wrong side of the equation.
In this example we are passing its name here and we simply copy that to this name field here
and that's
the right way to do it.
But imagine what it would look like if it was the other way around.
It wouldn't make sense.
That's why we use the key word here to make sure what we have on the left side of the
assignment operator
is a member of the class.
In this case the name field here.
So what we get from the outside which is in this case the constructor parameter will be
copied to the
name field.
OK with that constructor.
When we create a new instance of customer we can supply a name here.
At this point the constructor will be called.
And this string that is passed here will be copied to the name field.
We have a concept called constructor overloading.
Overloading means having a method by the same name but different signatures.
What do they mean by a method signature.
A signature is what uniquely identify is a method that has its return type its name and the
types and
numbers of its parameters.
In this example here we have three constructors so we have overloaded the constructor for
this class
each constructor as we see has a different signature.
So the first one takes no parameters.
The second one takes one parameter of type string.
The third one takes one integer and one string as parameter.
Note that the names here do not matter but the data types or the parameters and the Order of
them is
important.
So we cannot have two constructors with the exact same signature.
Now we would wonder why do we need to overload constructors.
The reason for that is to make initialization of this class easier.
Sometimes we may know only the name so we may use this constructor when creating an
instance of this
class.
Sometimes we may know both the ID and the name so we use this one or sometimes we may
know.
Neither of these parameters.
So we may use this constructor here.
OK lets start coding and see constructors in action.
OK lets start by creating a customer class so the public class customer.
Now we declare a field public integer ID and another one public string name before I move
on I need
to clarify something here in the real world applications.
We do not declare fields with the public access modifier as we see here.
This is just because I want to take things in a step by step fashion.
When we get to that lecture about properties we'll see a better way to declare fields.
For now let's just keep things simple and learn everything in a step by step fashion.
OK now let's put this customer class in a separate file here I'm using sharper.
If we don't have the sharper I highly recommend we to purchase a license for it because it
really
helps we with wer coding.
Note that I'm not a resharpen affiliate and I don't get a penny from promoting their product.
I just believe resharpen takes coding to the next level.
It makes it much easier and much faster.
All right let's put this class in a separate file.
So I put the cursor here.
I notice all I can hear now is use part refactoring.
That means changing the structure of the code without changing its functionality.
So here I pressed alternate enter and it pops up this context menu here.
The first item says move to another file to match type name.
So I just press enter.
I know that now we have a separate file called customer that C-s and this file is added to
solution
explorer.
So if I didn't have sharper I had to go here right click and then go to IDE and I know we don't
see
that here in this rain so I put the solution explorer to the left side.
OK so right click I add new item or a class which would open up this dialog box here and
then.
Here we had to type customer.
See.
It's really not a good and fast way because as a professional programmer we don't want to
switch to
mouse while we're coding.
We should learn to do everything the keyboard that's much easier and faster.
So let's not worry about creating a new file and use resharpening from now on.
I put this solution explorer back to where it was.
There we go.
All right.
Now let's go to the programs.
Yes we're in a console application and create a new instance of this customer.
So customer.
Customer A calls new customer or a better way is to use var instead of customer because.
Note that here we are repeating this customer word twice and that makes the code slightly
cluttered
so we can just use var here and let the compiler figure out that customer is of type customer.
So the code looks a little bit cleaner now.
All right now I want to show we the effect of the default constructor that the C-sharp
compiler creates
for us.
Note that here in the Customer class I did not create the constructor but I told we earlier in
this
alliance that the C-sharp compiler creates one for us.
So let's see what happens.
Let's display the fields of this customer class on the console console dot write line.
Customer thought Id and console dot write line customer name.
Note that the way I typed console dot write line was via what we call the code snippet which
is much
faster.
So I didn't type console dot write line I just typed C-w and press tab.
This is what we call a code snippet.
It's a quick way to write code.
There are many code snippets in C-sharp and I have explored many of them in my course
Dobler coding
speed that we can find a new enemy.
So let's move on for now.
OK now let's put a breakpoint here.
We can put a breakpoint using f 9 and we run the application in the debug mode using a 5.
OK I'm going to put a watch on the customer object here.
So customer let's expand this.
Note the default value is assigned to these fields here so Id is an integer and the default value
for
the integers or any other kind of numbers is zero.
Name is a string and the default value for strings or any other kind of reference types is not.
So this happened by the default constructor that the C-sharp compiler created for this class.
OK now let's declare a constructor and see how we can initialize this field upon instantiation
of a
customer.
So I stopped a debugger using shift and 5
we go to the customer class to do that.
I simply press control and tab.
Look we got the open windows here in Visual Studio.
I didn't have to go and grab my mouse go to solution explorer and double click customer.
All right now here let's declare a constructor to declare a constructor.
There are two ways.
There's no way to type public and the name of the class in the curly braces.
What is the fast way.
We type C or as in short or a constructor and not the icon for the code snippet here.
So that's a code snippet if we can press the tab or we go we've got the constructor.
So this is how I want we to code.
I don't want we to type every letter as a fast code or we should know all wer shortcuts.
We should code like a ninja.
OK.
Now just give a parameter to the constructor.
So I go here and say integer ID.
And here we need to copy that to our ID field.
So I type in these the notes here are the members of this class.
So here's our ID field because Id nullus overload constructor.
So I'm going to create another one with a different signature.
Again see tour.
Got Here.
Now this time I want to add two parameters into ID and string name.
OK now let's initialize them this that Id Akos ID this that name a code name.
Now if we go back to our program class again using control and type here.
Note that we got a red underline.
And that's because the compiler cannot find a default constructor that is parameterless.
So we can no longer create a customer object using this constructor because it doesn't exist.
So what does this mean.
That means because we created two custom constructors the compiler will no longer create
that default
or Rahmatullah constructor.
So if we still want to have this freedom to create a customer object without supplying any
parameters
upon instantiation we need to go back here and create a default or parameterless constructor.
So sæter that's it.
In this case I'm not doing anything here like to program.
Note that the red underline is gone but also when we opened the brackets here.
Note that here we have three overloads where the constructor one is without any prominence.
One takes an integer and one takes an integer and a string.
Let's use the third one.
So I said 90 to one and a name to John.
Now we are on the application
note that ID is initialized to 1 and name is initialized to John and that's the intention of using
constructors
.
OK now let me tell we a best practice.
Let's get back to our customer class C in this case our customer class has only two fields and
we have
created different variations of these constructors here for initializing these fields.
What if we had five other fields here.
Would we go and create seven other kinds of constructors or initialising.
Each of these fields.
No definitely not because that would create a lot of clutter in the class.
We only use constructors in classes in situations where we really want to initialize an object
at earliest
date.
That is really important for the object to perform in this simple example we have here.
It doesn't really matter whether the customer object has an ID or not.
Same goes for name.
We can always create a customer like here.
Let me remove these two parameters.
We can always create the customer object and then set the ID here.
It's not the end of the world John
but there are cases where we really have to initialize an object to an earlier state.
What is an example of that.
Let me show we.
So I want to create a new class let's call it order public class order.
Let's not worry about the fields in this class for now.
So I'm going to put this in a separate file with the cursor here.
Altan enter enter.
Done.
Now go back to the customer and the customer.
We want to create a list of orders so we use the list class public list of order.
And we call it orders in case we're not familiar with this list this list is a generic class that
takes
a parameter.
This is what we call a generic parameter.
So it represents a list of objects and this parameter here specifies the type of those objects.
So in this list we can store objects of type order.
Note that this list is declared in the system that collections the generic name.
And here because I'm using sharper as almost typing list of order resharpen automatically
added that
using statement on the top if we're not using resharpened we have to manually add this
statement.
OK let's move on.
As a rule of thumb and has a best practice whenever we have a class like here and that class
has a
list of objects of any type always initialized that list to an empty list.
What I mean by that is in the default constructor here we go and type order.
He calls a new list of orders.
Now we might wonder why I think the best way to explain it is by showing what would
happen if we didn't
do this.
So let me just comment this out.
To do that is with resharpen we can press control and slash If we are dissing resharpen
control K
control-C.
All right let's go back to the program.
Let's have a new order for this customer.
So I'm going to create var order caused new order.
Now let's say customer orders that I had this order.
If we run the application now it's going to crash.
We got an exception and null reference exception.
The reason this happened was let's close this because orders was not initialized and by default
because
it's a reference type.
It was set to No.
So when we called the add method on a null object we get no reference exception which is a
very bad
thing.
It's something we need to avoid at all times.
Now an amateur programmer may solve this problem by doing something like this here.
So saying order 30 customer orders a cost new list of orders
that may look like a solution but it's actually a bad solution.
In fact I wouldn't even call it the solution.
It's a hack.
It's a patch.
Why.
Because here in this main method here we should not be responsible for initializing that
orders list
to an empty list.
It's not the responsibility of this class here.
This class just wants to add an ORDER to this customer.
It's the responsibility of the customer class to make sure that these orders field is initialized to
an empty list and it's not a null object.
If we take this responsibility from this customer class and initialize that orders field
somewhere else
then it's going to be a problem because if every were in our code we are going to use a
customer object
we have to remember to initialize that orders field.
OK so I'm going to remove this line here and go back to the customer class in the default
constructor
.
I want to make sure that the orders field is always initialized to an empty list.
So that's the rule of thumb.
Whenever we have a class and that class has a list of objects.
Make sure that list is always initialized.
Now we have another problem here.
If we use this construct or here everything is good the orders field is initialized.
But what if we use either of these constructors here orders is going to be no.
Well we can go and copy paste this line into this constructors but it's not really a good way.
What if we had three other fields here that they all were lists.
So we had to copy pasted the re lines of code into each of these constructors here.
Is there a better solution.
Of course there is.
We can use this keyword.
Let me show we how it works.
So here in this constructor upon declaration I would put colon this and put the brackets like
this.
This means when this constructor is being called First is going to call the constructor without
parameters
.
So before this line is executed this constructor is going to be called which will initialize the
orders
field.
And then we get into this constructor here.
Let me show we another example to make sure we really nail it down.
So using a similar technique I can go to this constructor and call on this not that we have two
constructors
here.
Now we can call.
One is the default parameterless constructor.
One is the one that takes an ID.
I'm going to pass this idea that is coming here into this constructor and then get rid of this line
here.
What this means is when we use this constructor to initialize the customer object first is going
to
call the constructor that takes the ID parameter.
So we are going to go here and note that here before this code is executed we are going to go
here at
this point.
The orders feel will be initialized then we get back here.
The idea will be initialized and finally we'll get back here.
The name will be initialized.
So what I want we to learn here is that we can use these keyword and specify any of the other
constructors
.
We would like to pass the control to.
Now here we have a simple example and it's kind of ok to pass the control from this
constructor to this
one to this one.
But in general this is not considered a good practice because it makes the control flow a little
bit
complicated.
For example imagine someone else had written this code and we had to maintain it.
We look at this constructor and then we had to look somewhere else and then we had to look
somewhere
else.
It's a little bit ugly.
So what I suggest to we is keep the using of this in this way to a minimum and only define a
constructor
when we really have to initialize some fields of wer class.
In this example I explained to we that we really have to initialize this order field here.
So we created a default constructor.
I can argue that these two are really redundant and they're just making the code a little bit
ugly and
hard to maintain.
So it's OK to remove them but I'm just going to keep them here because I wanted we to learn
a few concepts
here.
One is the default and parameterless constructor and other one is the concept of overloading
constructors
.
That means we have three different constructors.
Each has a different signature.
And how we can use these keyword to pass the execution to another constructor in this class.
Well that's pretty much it for this lecture.
I hope we enjoyed it.
And thank we for watching

OK object initializers in the last lecture we learned about constructor's we know that we use a
constructor
to initialize an object and put it in an early state in C-sharp.
There is also another way to initialize an object and that is using an object initializer an object
initializer is simply a syntax or quickly initializing an object without the need to call one of
its
constructors.
Well we do need that simply to avoid creating multiple constructors.
Let me show we an example.
Imagine we have this person class with a bunch of fields.
Now this is a very simple example.
We only have four fields here.
In the real world application.
We might have a few more fields.
Now with this class if we want to create constructors for initializing various fields we may
end up
with a class like this.
So as we see here I have four constructors.
The first one takes only an ID.
The second one takes an idea and a first name.
The third one takes an idea with first name or last name and so on.
So we see there are so many different combinations and this is what we used to do in C-sharp
before
object initializers were introduced.
So as we seeing writing code like that is messy and easily becomes out of control.
So object initializer came to solve his problem with an object initializer.
We don't need any of these constructors.
We can't simply initialize a person object like this.
No these curly braces here.
I'm not calling one of the constructors of the Person class.
The syntax we see here is what we call object initialization syntax.
So basically we specify the name of properties and assign them some initial value.
Note that behind the saying when to initialize an object like this the default or parameterless
constructor
is going to be called.
And then any properties we set here are going to be initialized.
So with this way we can reserve constructors for scenarios where we really need to use them.
As I explained in The Last Lecture.
So an object cannot behave without being passed some initial values.
That's pretty much what we need to know about object initialization syntax.
The next lecture.
We'll take a closer look at our methods and their parameters.
I hope we enjoy this lecture and thank we for watching.

OK we go to Methot at this point we should know what a method is.


So I'm not going to review that again.
But in this lecture I'm going to cover some additional details about methods.
I'm going to start by explaining the concept of signiture for methods that I'm going to talk
about method
overloading which we should already be familiar with because I already talked about in the
lecture
about constructors but here we're going to see another example of overloading methods
which can be
useful.
Then I'm going to talk about three modifiers that we can apply to method parameters and
there are programs
ref and out of the three modifiers parameter is the only one that I consider useful in my
opinion.
Ref and out are bad decisions made when designing the C-sharp language.
There are code smells and a lot of developers have the same opinion.
Initially I didn't want to include them in this course because I didn't want to teach bad things
but
because I wanted my course to be comprehensive I decided to include them here.
Plus there are areas in the Dolphin framework where we have to use the Altamonte far.
So I want we to know how to use them even though I'm not going to advice we use out
modifier design
in wer classes and methods.
We'll see the results later in this lecture.
So let's get started.
What is a signature of a method.
The signature method consist of its name and the number and type of its parameters.
So in this example we see we have a point class that has a method called MOVE.
I have highlighted the areas where make up the signature of this move method with Jano.
So the name and the type and number of prompters.
A concept that goes hand-in-hand with the signature of a method is overloading.
So basically overloading means having a method with the same name but different signatures.
Look at this example here.
We have a point class with three move methods.
Imagine this point represents a point on the screen and we would like to move this to a
different location
so we can have three overloads of the move method one that takes two parameters of type
integer which
represent an x and y.
Another overload can take a point parameter and with this technique we makes it easier for
the consumer
of this class to choose the right overload.
Maybe sometimes we have two integers and it's more handy to call the first method here.
In other times we might have a point object and it would be easier to use the second overload
and also
here we have a third overload that takes a point and a speed which can create some kind of
animation
while moving the point from one location to another.
We don't always have to overload wer method but if there are cases where we see we can
improve wer
code and make it easier for the consumer of wer method overloading is a technique in wer
toolbox.
OK now that we understand the concept of method overloading.
Take a look at this calculator class here.
This class has at least three overloads for the add method.
The first one takes two parameters.
The second one takes three parameters and the third one takes four.
But as we see this is not an efficient way to overload the method.
What if we wanted to add two numbers together then we would have to overload the add
method 10 times
and that's a code smell.
Is there a better way to achieve this.
Of course there is the first step to make this code better is to use an array so instead of
overloading
the add method 10 times we can declare it only once and have it receive a parameter of type
integer
array with this declaration.
We can use the Add method like the example we see here.
While this works perfectly fine there is just a slight problem here and the problem is every
time we
want to pass a number of arguments to this method we have to create and initialize an array
or we have
to use the new operator and the into array notation.
So the big deal.
But there is a simpler way to do that.
And that's when we use the pro-ams modifier
so we can't change the declaration of our Add method to include the program's keyword here
just before
the integer array.
With that we can call this method in a couple of ways.
We can use it in the traditional form so we pass an integer array or we can simply pass
varying number
of arguments here.
We don't need to create and initialize an array and that's simpler.
Again this is not something that we use all the time but if we have situations where wer
method might
need a varying number of parameters we can use the prom's modifier to make it easier for the
consumer
of a method to call that method.
OK let's take a look at the ref modifier.
This is probably the only example in this course where I'm going to use names like my class
and my method
because I really don't like this kind of teaching.
If we have noticed I try to use real world examples that make sense as opposed to abstract
names like
my math.
My class one too.
It just doesn't make sense anyway because the ref and modifiers are what they call a code
smell.
I couldn't think of a real world example to demonstrate this concept here.
So let's just imagine this my method here takes an integer and whatever we pass it as to that
integer
.
Now take a look at this example here.
That's what we would right to call that method.
Now I have a question for we.
Here we have set a to one we call my method and pass 8.
What do we think would be the result of a after returning from this method.
Is it going to be three.
No it's going to be one because eight is a value type.
And that means when we pass to a method like the one we see here it's value is been copied.
So the aid that we have here is a local copy of A that will be relevant to this method here.
It will not affect the origin on aid that we had here.
We can change this code by including a ref modifier to our method and note that here I
change the name
of the class and its method from my class on my method to weirdo and do a weird thing
because it just
is weird.
So with this chain if we call this method and also include the ref modifier here the original A
that
we have here will be passed to this method and its value will be modified.
So after we return from this method the value of A is going to be 3.
I'm completely against this concept.
I think it's a code smell.
And I want to make sure that we're never going to use this.
But if there are classes written by other people or perhaps somewhere in that framework
where a parameter
is defined with the ref modifier I want we to know that in order to call it method we need to
specify
the ref modifier here.
Honestly I can't remember on top of my head whether we have places in the dotted
framework where methods
are defined with the ref modifier but that's all I want we to know.
Now let's take a look at the money for now our modifier is slightly similar to the ref modifier
in the
sense that if a parameter is declared with the out modifier as we see here then in order for we
to
call that method we also need to specify out when calling that method count is conceptually a
little
bit different from ref.
What does it mean.
That means with the out this method can return a value to the caller.
Now we may be wondering could it just return a value here instead of using void.
Absolutely yes.
But with our keyword we can have multiple parameters here and they all can return a value to
the caller
.
And that's exactly where I say this is a code smell or this is a design smell of the C sharp
language
because if a method is going to return multiple values to the caller it's better to encapsulate all
these values into a separate class which could be the return type of that method.
So again I want to emphasize Do not ever use the modifier when designing or method but I
included the
modifier here because there is one place in dot net framework that we might be using
sometimes and
that's where we have to use the out modifier even though it's not a good choice but I want we
to be
aware of that.
OK.
We know theory.
Let's start coding and see all these concepts in action.
OK let's start by creating a point class.
So public class Point this point represents a point on the screen so it needs two fields an X
and Y
and they both have to be an integer of public and X public and Y.
And here we should create a constructor to initialize these fields.
So Souter type we get two parameters into x and y and there's that X because X y equals Y.
Pretty simple.
Now let's put this class in a separate five to clean up our code.
So the cursor is here with recharter.
We press alter enter and enter again.
Now point is in a separate file.
Now let's add a method to move this point to a different location.
So public void move when the two parameters and X and Y and we simply change the value
of our fields
using these arguments so these that X equals x y y.
Now we can overload this method by creating another version of that that takes a different
signature
.
Maybe the other one takes a point object.
Let's see how it works.
So public void move here repasts a point object that it is a new location and we use this
object to
change the value of our field so that x he calls new location x.
Is that why.
Because new location that way.
Now let's go to our program class.
So we simply press control and tab to switch between open windows.
There we go.
Let's create a point object bar point because near-point and I give we an x and y or 10 and say
20
.
Now if we call the move method points don't move.
Look we've got two versions of this method.
So there are two overloads.
The first one takes a point object.
The second one takes an x and y.
Sometimes in our program we might just have two numbers whereas other times might have
a point object
.
So by overloading this method we make it easier or the color of this method to pass
arguments to this
method.
So let's try both versions for us I pass a point object.
Let's move it to 40 and 60.
Now to ensure that everything is working let's put the value of X on Y on the console.
So CW type again this is a code snippet if we want to learn more of this fast coding
techniques.
I have a course called Double wer coding speed and we tell me where I teach we lots of
techniques
to write code fast.
So here in constant dot write line we can say point is at and here we pass the location so point
x point
that way.
Let's run the application with controller F5.
OK point is at location 40 and 60.
So our move method is working properly.
Now let's extend this example and this time use the other overload of the move method.
So point dot move. This time I want to move it to 100 and 200.
So I use the second overload.
Again this copy paste this line here and make sure everything is working.
We run the application.
OK.
So our point is moved twice and know it's at location 100 and 200.
So this is how overloading works.
What I want to show we that there is a problem with this code in terms of best practices.
Let's get back to the point class.
OK here we are duplicating the concept of setting x and y.
Now this is a very simple example and we are just setting two fields are sometimes in more
complicated
scenarios.
It's not a good idea to repeat the same concept in two places.
So what we can do is to make this move method call the other move method.
This way we set x and y in only one place.
So if there's a bug in our program there's one place that we have to fix.
Let's see how we can implement this.
So here I simply call the other method and I pass new location that X new location Y and we
can get
rid of these two lines here.
Looks better doesn't it.
But there's still one more problem with this code.
Can we spot it.
And to give we a hint it's here there is one tiny problem here.
The problem is if we pass a null object here this method is going to throw an exception.
Let me show we what I mean by that.
So we go to program.
I'm going to change this line.
So instead of passing a point object a pass.
Now
let's run the application.
There we go.
The application crash and we got a null reference exception.
In case we are not familiar with exceptions exceptions are Dartmouth's way of error
reporting.
I've covered exceptions in full detail in my C-Sharp my advanced course that we can find on
me.
So let's move on for now.
We go back to the point class here we need to validate the argument that is passed in.
So we make sure that it's not known.
Otherwise if we go no dad extra or not but why we are going to get a null reference exception
we go
.
If new location is null we throw an argument no exception and past the name of the
parameter.
What does this mean.
First of all throwing that exception is a way to report errors to the caller.
So here I used to throw key word here.
I create a new exception object.
An exception is just a class.
And here it's just instantiating that class and in the constructor here I simply pass the name of
the
parameter that was not.
In this case new location with this code if new location is no we're never going to get here.
So the state of our class which means that x and y is not going to be changed.
So this way our point object will always stay in a valid state.
The technique I have used here as invalidating this argument here is called defensive
programming which
is actually beyond the scope of this course but basically a defensive programming improves
the robustness
of wer code.
OK now let's run the application and see what happens.
Look the application crashed again.
But the difference is this time we got an argument Knol exception as opposed to a null
reference exception
.
So we would argue how is it different.
Well it's better to get in an argument an exception than not reference exception.
Why.
First of all wer application will always have a global error handling mechanism.
The reason our application crashed here is because we don't have a global error handling or
exception
handling mechanism.
I will show we how we can do that in a few seconds.
But the point here is when we get an argument or an exception are immediately telling the
caller of
this method that is this move method that the value they have passed in is not a valid value
and as
a result no further actions will happen.
That's the idea of writing robust code.
If we get some invalid value whether it's Nall or some value that is out of range or maybe
somewhere
we don't expect a zero or an empty string.
Then if we get that value and do operations on that value we're taking wer program to an
unexpected
state which means some weird things may happen down the track.
So the idea of defensive programming is to stop the program from getting into that weird or
invalid
state.
OK now let me show we how we can improve this code by I a global exception handling
mechanism.
So the application will crash.
Let's get back to our program.
Simply I add a try block here is simply type try and press tap.
Let me show we again.
Try tap.
So again this is a code snippet.
We immediately get it try and catch block the code that may throw an exception should be
placed in
the try block.
And if an exception is thrown and this catch block will be executed.
Don't worry about this.
Throw key word here just remove it again.
I have covered the exception handling in more detail in my C show of adman's course but just
to give
we some tips here.
What we need to do is simply put the message on the console saying an unexpected error
occurs.
If we run this application the application doesn't crash and we get a friendly error message.
This is better in terms of the user experience.
We don't want to write an application that crashes.
No one likes that.
OK.
I'm going to move all this God into a separate method.
So static void use points and I take everything here
and pass it here.
OK now let's go and create a calculator class.
So public class calculator
we want to create a method call and that takes a varying number of arguments.
So the public into that we know we add the prom's keyword programs and then an integer
array and the
name of the parameter is going to be numbers.
Now inside this method numbers is an integer array.
So let's say we have an integer array and we want to add all the numbers in that array together
and
return the result.
First we create a variable called some say to 0.
An RV is a four inch log to iterate over the numbers
and simply add it every number to the sum.
And finally we return something when we get to that best level.
There is a better way to write this go.
And that involves using link or language integrated way.
It's one of the powerful features of C-sharp.
Again I have covered it in my C-Sharp advanced course.
So now let's just keep the code the way it is.
Now we've put this class in a separate file.
So Altan enter and enter.
Now we back to the program.
Let's create an instance of the calculator bar calculator.
Now we can call the add method like passing two numbers and we can simply display the
result on the
console.
Or we can pass three parameters or four or whatever it's up to we.
We can pass varying number of parameters and that's the effect of the prom's Keyworth.
We can also call this method using an array notation.
So that means they start again here in that I can pass a new integer array and put all numbers
here
.
But as we see it's easier to simply pass all the parameters without the need to create an integer
array
.
And that's why we use the pro-ams keyword.
OK let's put this code in a separate method and move to our third example.
So I'm going to create another static method here use for.
Let's move everything here
right.
The third example involves using that out modifier.
I told we to not use the alpha modifier and declaring wer methods but there are cases in the
data
frameworks where we may have to use the money for.
So let's see an example of that.
Let's say we have a string and we would like to convert it to a number we can use to parse
method of
the integer class.
So to tap into that parse and pass an invalid string here that cannot be converted to a number.
I store the result in the number variable and on the application
look the application crashed.
We got an exception a format exception input string was not in the correct format.
Let's take a look at the try parse method.
So in a try parse look it has two overloads.
The first one takes a few parameters.
The second one takes only two parameters.
So I'm going to use the second one it's easier.
It takes a string and that is the string we will like to convert.
It takes an integer that is decorated with the out modifier which will have the result of
conversion
if successful.
And finally the returns are bool which indicates whether the conversion was successful or
not.
So let's pass the string here ABC and here we need to pass an integer so int number and
because it's
declared with the out modifier we need to use the our key word here or number and it returns
and pull
.
So var result.
So if conversion is successful result will be true and we can check that and display the
number on the
console.
Otherwise we can say conversion failed.
Let's run the application.
So look we got a message called conversion.
Now how is it different from the Parse method.
The difference is tripartite does not throw an exception and that's the reason it returns a
boolean
to indicate whether the conversion was successful or not.
The downside is that we have to declare this integer separately and then use the money for
some people
don't like to try parce method and they prefer to use parce But then we have to handle
exceptions using
a try catch block.
As we learn a little bit earlier something like this here we would say one version failed these
two
pieces of code are kind of equivalent.
Now this number is actually declared somewhere else so let me change it to just numb.
There we go.
So here are two examples.
I hope we enjoy this lecture.
And thank we for watching

OK we got two fields at the beginning of this section.


I gave we a brief explanation of fields if field is like variable that we declared at the class
level
and we use that to store data about the class.
So in this lecture I'm going to talk about a couple of different ways to initialize fields and
then
I'll talk about the concept of Read-Only fields.
So in the last lecture we saw me declaring a class called customer which had a list of orders.
And we also saw how I initialized that field using the default or the parameterless
constructor.
While this I purchased perfectly fine.
There is also another school of thought when it comes to initialising fields.
Some developers believe we should use constructors only when we need to initialize our
fields based
on the values passed from the outside.
So in this case we're initializing the orders field without any external varios the constructor as
we
see here has no parameters.
So in situations like that there is another way to initialize the orders field and that looks like
the
code we see here.
So we can directly initialize the orders field without the need to create a constructor.
This approach has an extra benefit and that is we can have multiple constructors and no
matter which
one is called the orders field will always be initialized to an empty list.
We'll explore that later when we start coding.
OK now let's take a look at the read only fields.
We can declare a field with the read only modifier to make sure that that field is only
assigned to
once.
So in that case that field has to be initialized either directly like this.
Like we see here or in one of the constructors of the class.
We might wonder why do we need something like that.
The reason is to create some kind of safety in our application to improve robustness.
For example take a look at this customer class here by declaring the orders field as read only.
I'll make sure that I will only have one list where we will keep the list of orders.
If I accidentally as a developer try to re-initialize this field in another method the data that we
had in the field will not be lost.
It's easier to explain that using an example.
So let's start coding and see those concepts in action.
OK let's start by creating a customer class
so public class customer.
Now let's declare a couple of fields so public and to ID public string name
we can also create an order class public class order.
I'm going to leave the implementation of this class for now.
We don't really need it for this example.
All we need to do is to create a list of orders and the customer so public.
List of order.
Now let's declare a couple of constructors for this class.
So sæter the first one may get just an ID so that Id cause Id The second one is going to get an
ID on
a name and just to recap what we learn in the constructors lecture.
We can use this key word here and instead of repeating the initialization of the ID like the
code we
see here we can delegate the control to this constructor here so I'm just going to use the this
keyword
has to ID.
At this point.
This constructor will be called so the ID will be initialized based on what we get here and
then here
I can say this doesn't name a cause name.
Now if we remember from the lecture about constructors I explained why we need to
initialize these
orders to an empty list.
Just to recap whenever we have a class like customer and inside the class we have a list.
We should always initialize that list to an empty list.
Now the technique I showed we in that lecture was to create a default constructor like the one
here
and set the orders for an empty list like here.
This approach is perfectly fine.
There is a slight problem with that and that is if we use any of this constructors here so this
one
or this one.
We have to make sure that the default constructor is always called first.
So the orders fill will be initialized.
Some developers argue and say no we shouldn't initialize it feels like the orders here because
orders
is not dependent on any parameters from the outside.
So what we can do is we can get rid of this constructor and initialize the orders field here.
This way no matter which constructor is going to be called the Order spell will always be
initialized
.
An empty list.
Some developers do not like this approach because they don't like the idea of initializing
some of the
fields here while declaring them versus initializing the others in the constructors.
It's entirely up to we.
It's more a personal taste.
I wanted to show we both approaches.
So we know what is possible.
The approach we choose is up to we.
But what I want to emphasize to we is to be consistent with wer approach.
Make sure we use the same approach everywhere.
This way wer code would be cleaner.
OK now just move on and look at read only modifier.
So here I want to declare a method let's call it promote and the intention is.
This method will promote this customer to a gold customer.
I'm going to leave the implementation here.
Let's just put some comment but I want to show we a mistake that I as a developer can
accidentally
make.
Let's say if I accidentally re-initialize this order orders here what would happen.
So what I'm going to do is to clean up our code.
I'm going to put this customer class in a separate file so cursor here.
I explained this earlier.
So with resharpen alternate enter and enter again.
Now this class ended up in a separate file so that file is.
Customer.
Yes now we go back to program.
We can do the same with the order class.
Back to the program.
Now the code is cleaner.
Let's create a customer object.
So our customer calls new customer we are expected to supply an ID and or a name because
we don't have
a default or parameterless constructor.
So look here we've got two constructors and one to use the first one.
Doesn't really matter.
I'm going to add two orders to this customer so customer support orders not add new order
let's just
copy paste this line.
So at this point if I displayed the number of orders the customer has we should see two on the
console
.
So let's quickly do that.
Customer orders that count.
Let's run the application.
So we got two on the console.
Now let me show we something.
Imagine here we make a call to the promote method.
This method because of a bug accidentally re-initialize the orders field.
So now if we run the application all the data that we had in the orders fill is lost.
We have 0.
This is where we used the read only modifier.
So let's go back to the customer if there are situations where we know that this field should be
initialized
only once.
That's where we decorate that with the read only modifier.
This way if we accidentally reset that field in the code we're going to get a compile time
error.
First of all we can immediately see this error here by the red underline.
It says read only field cannot be used as an assignment target.
So if we don't see the read error when we compile the application we're definitely going to
see that
.
So a read only field cannot be assigned to except in a constructor or a variable initializer.
So what this means is this line is not acceptable and we can only initialize a read only field
either
here directly when we are declaring that or in the constructor.
So Read-Only is one of the ways that we can improve the robustness of wer application.
That is for this lecture.
I hope we enjoy it and thank we for watching.

OK access modifiers So far we have seen me declaring classes and their members with the
public key
word public is what we call an access modifier in C-sharp we have two ready five access
modifiers public
private protected internal and protected internal.
And this lecture I'm going to talk about public in private and we'll leave the rest to when we
get to
the lecture about inheritance.
So what is an access modifier and access modifier is a way to control access to a class and or
it's
members.
Now we may wonder why do we need to control access to a class or its members.
The reason is to create some kind of safety or guarding our applications to improve the
robustness in
the lecture about feels.
I explain how we can use the read only modifier to make sure that the field is assigned only
once.
And this way we developers will not accidentally create bugs in our code.
Take a look at this example here.
I have declared a customer class with a name field that is declared as private with this code.
When we declare an instance of the customer we cannot access the name field so we cannot
go John dot
name that will not compile.
Now we may wonder why do we need something like that.
Well that's the beginning of object oriented programming and object oriented programming
which is actually
one of my absolute favorite topics.
We have three major concepts encapsulation which is also referred to as information hiding
inheritance
and polymorphism.
In this lecture we're going to learn about encapsulation and throughout this course we'll see
more examples
of that encapsulation.
We're going to leave inheritance and polymorphism to the later section in this course.
Let's start with encapsulation.
I want to use an analogy think of a restaurant in a restaurant we have several roles.
We have a cashier we have a manager.
We have a chef.
We have one or more kitchen hands.
We have one or more waiters or waitresses and all these roles collaborate together to provide
an amazing
experience for we.
Well hopefully because sometimes we go to a restaurant and we come back very
disappointed.
But anyway think of the interaction between a waitress and a chef.
A waitress takes the order and passes it to the kitchen and the chef looks at the order and does
his
job and when he's ready it notifies the waitress so that chef is responsible for a few things
which
is outside the responsibility of the waitress the waitress is not going to go to the kitchen tell
the
chef how to chop the vegetables and how to cook the meat.
And I don't know about different spices.
Each of these roles are responsible for their own things.
They have some knowledge and some capabilities that perform some functions suffer should
be the same
in sulfur.
We don't have a chef or a waitress but we have classes and these classes collaborate to
perform the
functionality required from the application.
Now we want to design our classes such that each class is responsible for one thing it does
only one
job and does it perfectly.
We want our classes to hide some of the information about how they do the things they are
responsible
for.
We don't want other classes to know about the details of other classes.
And this is what we call encapsulation.
So we want to encapsulate some data in terms of fields as well as some behavior or
functionality in
terms of methods and classes.
And we want to hide the details from the outside.
So when it comes to fields we want to declare them as private and provide methods that
would give access
to these fields.
We call these methods getters and setters and these methods are going to be public.
So we think of fields as the implementation detail which should be invisible from the outside.
It's how a class store something in memory.
We don't want any other classes to know anything about that.
So to show we an example here we have a person class that has a name field that is declared
as private
.
So with this code if we create an instance of the person class we can access the name field of
that
object.
Instead we need to call one of the methods here said name or get any look at the set named
method here
.
The interesting thing about this method is that it does a check before assigning the name field
of the
person.
So if the value that is passed to this method and as the argument is null or empty it's not
going to
set the name field.
And this is one of the advantages of providing setters and getters.
We can know that we have the same thing with a field if field is purely storage in the
memory.
It doesn't have logic with a setter or a getter.
We can have some logic when accessing that field.
OK.
Before we start coding I just need to emphasize something here in terms of naming
convention in C-sharp
.
We have two naming conventions.
One is called Pasko case.
The other is called camel case with Pasko case.
The first letter of every word should be opera case.
Like the person here or name or certainly not that the first letter of every word is uppercase
with
camel case the first letter of only the first word is going to be lower case.
But the first letter of every word for that is going to be uppercase.
An example of camel case is the name parameter here.
So the first letter is lorikeets.
Now when it comes to classes we need to use the Pasko case when naming the class or any of
its methods
for fields.
The convention is to use the camel case prefix with an underline.
So we need to change the name field here to something like this.
So private fields should start with an underline and they should follow the camel case.
OK I think that's we know theory let's start coding and see all these concepts in action.
OK let's declare a class called person.
And know we can declare a field called birth date which should be of time day time but we
no longer
are going to declare a field as public.
Instead we're going to use private so private data time
Birthday.
No that I have used and I underline here and Kemel case.
So the first letter of the first word is Laura case.
Now with this code we cannot access to birth date field outside the person cause.
So if we go to the main method here and create a person object
person dot c we don't see the birth date field.
It's hidden from the outside.
And that's what we mean by information hiding in object oriented programming.
Ok then how do we set the birthdate for that to happen.
We need a method.
So many movies for now I can do a person class and define two methods.
Public void set birth date and this method takes a parameter of type day time and we call it
birthdate
.
At this point if there are any logics around birth date we can implement them here.
In this case we're going to keep things simple.
We don't necessarily need the logic or unbirthday that this point.
So what we need to do is simply set the birth date to the Valeo pass to this method
and we declare another method of like date time
get birth date and this method simply returns that birthday feel.
Now with these two methods we can go back to the main method here and say a person that
set birth date
we can say new date time 1982 1:1.
And of course we can read the birthdate.
So cancel that right.
Line person God get Versteeg.
We can run this application.
And we got the birth date on the con..
OK I know what we're thinking we probably are confused why we changed the axis modifier
for birthdate
to private but then gave two methods here that directly modify the field or return this value.
How is it different from directly going to that field.
Well if that's what we're thinking it's in fact a good question.
That's one of the questions.
I also have when I started with object oriented programming the answer is objects are about
behavior
about what they do their fields is primarily their internals their implementation detail which
should
be hidden from the outside world.
Even though in this example it doesn't really make a difference whether we have a public
field or a
private field with two methods.
But from an object oriented perspective we want to follow the principle of encapsulation
which suggests
that objects should hide their implementation detail and reveal what they can do as opposed
to how they
do what they're supposed to do.
We the examples always show we for this course we realize the importance of this concept
more and
more.
Well that's it for this lecture.
What I want we to take away from this lecture is we're going to declare our fields as private
and
the naming convention is under line and Kemel case in the real world applications we are not
going to
define two methods like the ones we see here.
This was purely for demonstration and because I want to take things in a step by step fashion
in the
next lecture I will show we an easier way to achieve the same functionality.
And that's what we call properties.
I hope we enjoyed this lecture and thank we for watching

In the last lecture we talked about fields and encapsulation.


We learn how to write a getter and setter and this lecture recone to continue that topic and see
how
properties can help us achieve the same thing with less code.
So what is a property a property as a class member that encapsulates a getter and a center for
accessing
a field.
So why do we need a property simply for creating a getter setter with less code.
So let's see how we can write a property.
Here's the code we wrote in The Last Lecture when we were working with fields.
So to recap we have a Person class which has a birth date field which is declared as private
and we
have two methods year set birth date and get birthdays which provide access to this field.
As we can guess from this example writing these two methods for every field is a little bit
time consuming
and tedious.
Imagine if this class had five more fields we would end up with ten accessor methods and
that's not
really efficient.
So we can achieve the same thing with a property if we want to convert this code to use a
property instead
of two accessor methods.
This is how the code is going to look like.
So we still have the birth date field which is declared as private.
And here we have the property.
Note that the property is declared as public and it should have the exact same data type as
their field
in terms of naming convention.
We use Pasko case for naming properties.
So the first letter of every word should be uppercase.
A good way to remember this is when where we're working with classes.
We should use Pascola case in most cases.
So the class name the properties and the methods they all use Pasko case.
The only cases where we use camel case is private fields as we see here.
We should also be prefix and an underline and another case for camel case is the method
parameters.
OK let's move on.
I look at our property here.
So inside this property we have a get method and I said method.
Note that the get and the said here are C-Sharp keywords so they should be lower case and
they have
a code block as we see with the curly braces here in say the get method.
We simply return the field and inside the said method we used the value keyword to get what
is on the
right side of the assignment and copy that to the birthdate field here.
Note that in this case we don't have any logic around the birthdate field.
So our get and set methods are pretty simple.
We can write even less code to achieve the same thing.
That's when we use auto implemented properties.
So here is how we can declare an auto implemented property.
So we have the property declared here public a time birthdate and there is no field.
We just have to get semi-colon and said semicolon.
When C-Sharp compiler sees that internally it creates a private field for us.
So we don't have to do that.
OK I think that's enough theory.
Let's start coding and see all these concepts in action.
OK let's declare a person class first.
So a public class person we want to represent the concept of birth date for this class.
So I'm going to just go ahead and declare an auto implemented property without declaring a
field so
public day time birth date.
We open the curly brace get semicolon and set semicolon with this code C-Sharp compiler
internally
creates a private field and implements the get and set accessor methods for us.
Let me show we how it works.
So I'm going to compile this application to compile we press control shift and B.
So build succeeded as we see here.
Now we go and right click on the project.
Note that here I have an item called Open command prompt.
If we don't have this in wer Visual Studio we need to install visuals to we productive with the
power tools.
It's an extension to Visual Studio which makes coding a little bit more pleasing and easier.
So how we can find it is we go to Tools extensions and updates we go into online and in the
search
box type productivity power tools
there we go.
Know that I have installed this plug in.
And that's why we have this green take here.
So in wer case we probably have to click it and then we select download.
We probably have to restart Visual Studio.
Then we will get is open command prompt and the benefit of that is it takes we directly to
where the
project is.
Without this tool what we need to do is to go to start open command prompt and use see the
backslash
whatever to find that directory where the project is located.
OK.
Now I want to show we the actual code that is generated by the C-sharp compiler behind this
auto implemented
property.
So first let's take a look here are we've got a bin folder we go to bin the Earth City de-bug.
This is where the compiled files are the assemblies are located.
So it can look McLindon up.
So here we have got properties dot exe and the name of this project is called properties and
that's
why we got these properties that exist here.
It's an executable it's a console application.
Now what we need to do is we type I L D A S M that stands for I l this assembler Io's stands
for intermediate
language and that's the target language that the C-sharp compiler translates wer code into any
language
that targets Duckman framework eventually translates code to l in Dathan framework.
We have a component called C L R or a Common Language Runtime.
And what it does is at runtime it takes wer code and translates that into the native or binary
code
for the machine on which it's running.
So let's take a look at the code and see what it looks like.
So when I disassembler we can here pass the name of the executable or the assembly
properties X Z.
So here is a I l the as well that here is a namespace properties.
We expand that.
We have two classes person and program.
Let's actually put this here.
OK so here is our Person class and here is the Program class I expand the Person class.
Note that here we have
what is called a backing field.
It's private and is of type day time.
This is the private field that the compiler automatically created for us.
And here we have two methods gets underlined birthdate and set underline birthdays which is
similar
to the code that we saw in those slides and here is the property.
If I double click that note that it has a good pointer here which simply calls the get birthdate
method
.
It also has a set pointer here which calls the birthday birthday let's close this.
Also note that here we have a constructor and that's the default constructor that I told we of
the
C-sharp compiler creates for us the job of this constructor is to initialize the class to an early
state
.
So it set all the fields of this class to their default values.
All right let's move on because this I want to show we a few important things here.
First with the cursor here let's declare a property called H.
So public and age this property cannot be an auto implemented property.
Why.
Because here we need some logic.
I want this age to be based on the birthdate of that person.
So if I just type get and said here internally the compiler would create a private field and that
the
H field will not be based on the birthdates.
Instead what we're going to do is
create a get accessor method here and here we are going to have some logic.
So what we need to do is to get today's date so date time today and we subtract that from the
first
date when we subtract two Daytime objects.
We get a time span.
So let's store the result in a time span.
Note that if I over my mouse here on the VAR we'll see the data type of this object called
time span
is time span and time span represents a generation.
So I can't get the time span dog days and divide that by 365.
And that would give me the total number of years.
And finally I would return to that before we move on I would like to put this class in a
separate five
to clean up my code.
So cursor here.
alt and enter enter.
Now back to our program class.
So let's create an instance of the person class or person because new person we set the
birthdate person
first date equals new day time 1982.
1 1 nounless display the age on the console console dot write line person.
We were on that purgation 33.
Now let's get back to the person class now live here in the age property I just declared a get
method
.
I didn't declare a set method and that was intentional because it doesn't make sense to set the
age
of a person the age should be calculated based on the birth date.
So with normal properties like the age property here if we don't want that property to be
citable we
just don't declare a set method.
But what about auto implemented properties.
Let's say we have this requirement in our application that the birthdate of the person should
be set
once and it cannot be changed.
So how can we achieve that with that requirement.
What we need to do is to go in this property and put a private accessor before the set method
with this.
If I go back to the program
we'll see this red underline here and the tooltip says the property birthdate cannot be used in
this
context because the set accessor is inaccessible.
So then how do we set the birth date.
We have only one place and that's the constructor.
So we need to create the constructor for this person class where we get the birthdate and we
said this
property and that's it.
The property can no longer be changed so let's declare a constructor see tour type.
Here we get a date time parameter date time called birth date
and we set the birth date property at it back to the program.
We had to modify this go because now we have a constructor that takes a parameter.
So I'm going to select this code and put that here and then get rid of the date.
So let's review this again in our Person class.
We have two properties here.
One is and how to implement a property which doesn't have a backing field.
This property has a private set accessor which means it's really only we cannot change it.
And we sit back in the constructor here.
We also have another property which doesn't have a set method either.
This property calculates the 8 based on the value of another property.
What I want to emphasize in this lecture is we should make sure that wer classes are always
in a valid
state.
That's the key.
Wer classes should never lie.
They should never be in a false state.
In the example here I have implemented this concept using a private accessor here and by
removing the
set accessor in the H property.
So this person class this person object is always in a valid state.
We said it's birthdate.
It cannot be changed.
And the age is calculated based on the birth date.
OK.
Before we finished this lecture I want to show we two more things.
First I want to show we a quick way to declare properties.
And next I want to tell we about the convention we should follow in C-sharp when working
with classes
on their properties.
So let's say we want to declare an auto implemented property called name for the person
class.
So what I'm going to do is go here on the top instead of typing public street name Curly brace
get said
I'm going to do a shortcut.
So let's get rid of this.
I just type prop as in short for property and first type.
That's a code snippet.
Now note that the type is highlighted.
So here I type in string.
I press tab again now to identify areas highlighted and I give it a name.
And finally I press enter.
That's it.
This is much faster.
Let me do this one more time without explaining it
isn't faster than typing the whole thing.
So that's one thing.
Now another thing is in terms of convention we might be wondering where should we declare
our properties
at the top on the bottom in the middle.
Well actually I made a mistake here.
This birthday property should be on the top.
So what we need to do is we put all our properties on the top then we have the constructor
and know
that there is a vertical space between all these properties and the constructor if the code was
like
this it would look a little bit squashed it looked dirty and ugly.
So always declare all wer auto implemented properties on the top of a vertical separator and
then put
the calculated properties on the bottom.
Well that's it for this lecture.
I hope we enjoyed it and thank we for watching.

OK we go to indexers.
What is an indexer.
A mixer is a way to access elements in a class that represents a list of values.
What do we mean by that.
Well let's take a look at a few examples.
We have all of the work by indexers.
Here are a couple of examples.
So here we have an array of integers and this is an indexer so we can access the first element
of an
array like this or here is a list a list of integers.
And again here using an indexer we can access the first element in this list.
Now we might say we all have the concept of lists and arrays and collections.
So we're not going to reinvent the wheel.
Why do we need to define an index or in our class.
Well sometimes we have classes that have collection semantics.
For example think of an HTTP cookie. An HTTP Cookie in case we're not familiar with that
is a file
that is sent from wer browser to the web server upon each request.
We have developers use a cookie to identify a user.
We can store some settings about the user in that cookie in the cookie.
We have a list of names and values.
So imagine in a project we have implemented the concept of A should to be cookie.
Now the code that consumes are AC to be cool typically class might look something like this.
So here we are creating an instance of the typical new class.
We set the expiry date.
And here is where we can use an indexer.
So it is a mixture.
I'm specifying that the name of the user is Marsh.
Done an indexer.
We have to write a method like that item here and pass a key value.
We'll see that achieving the same thing with an indexer is easier and requires less code.
If we want to get the value of a cookie item using an indexer.
Here is what the code would look like.
So we simply use the indexer has the key and we get the value without an indexer we have to
write a
method like get item.
Again the code that uses an indexer is easier and shorter.
Now in real work projects it's unlikely that we're going to create an be Kahu class because it's
already
part of darkness framework.
But I use this as an example in case we're working with a class that has the semantic of a list
or
a collection or a dictionary.
That's where we can improve wer code by using an indexer.
It's not something that we may see everyday in wer career but I want we to be aware of this
feature
.
Now how can we declare an indexer and indexer is nothing but a property.
So we can declare an indexer exactly like how we declare a property.
So we have the data type like string.
Then in sort of an identifier we use that this keyword.
And here is the index or notation.
So brackets and inside the bracket we have the type of indexer.
So in this case with the typical key I want to find items by the key which should be a string.
So my indexer here is a string and I give it the name of key.
The rest is exactly like declaring a property.
We have a get method and a set method.
And here rewrite the logic for accessing that particular element.
Let's start coding and see this in action.
OK.
We first start by creating an HTTP Cookie class
and the typical key.
Now I'm going to put this in a separate file.
I've already learned that before alt and enter enter.
OK now we need a field to store the key value pairs in the cookie that data type or the data
structure
we use for that is a dictionary.
If we're not familiar with a dictionary it's a data type that resize in system that collections that
generic and it uses a hash table to store data hash table has a special mechanism that makes it
extremely
fast to look up an item by its key.
So whenever we have a list of objects and we want to look them up by a key as opposed to an
index
we should use a dictionary if we have a list of objects and we would like to look them up an
index
and a list is a better choice.
OK now let me declare a dictionary private dictionary.
I want this dictionary to be of type string and string.
Now what this means is this is a generic class.
This is a generic class and these are generic parameters and these parameters specify the type
of the
dictionary.
So in this case I'm specifying that the keys should be of type string and their values should be
all
soft type string.
OK.
Now let's give it a name dictionary.
I like to initialize this in the constructor dictionary.
It calls new dictionary.
That's it.
Just want to recap what we learned earlier.
We could potentially go and initialize this field straight here and that's perfectly fine.
It's entirely up to we.
We can do it here or in the constructor.
Now back here.
OK.
Now we need an indexer.
Declaring an index is exactly like a property.
So what are we going to do.
Is the public the return type string because we have key value pairs and they both are string.
So string now an index doesn't have a name.
We use that this keyword.
So this and here's the index or notation we use string to present the keys for our key value
pairs.
So strange.
Key and here inside this property we have a get and set method.
Now the implementation is very easy.
All we going to do is to delegate to that dictionary.
So for yet we're going to return dictionary of key.
So internally we rely on the dictionary to store the key value pairs and to be Kuki is simply a
wrapper
around that ellos implement the set method.
Again very similarly dictionary of key.
It calls value and this value is a key word which represents what is on the right side of the
assignment
operator.
Notice green on the line here.
That's resharpen highlighting feature.
So if there are areas in the code that can be improved resharper highlights them with a green
underline
.
In this case it's saying field can be made Read-Only and this is a great example of using read
only
because we don't want to accidentally re-initialize that dictionary and lose all the data be
stored
in it.
So here I can just press alternate enter and let resharpen apply the read only modify for me.
There we go.
So as we see with resharpen we tend to code less and we can delegate a lot of things to
sharper.
OK now this is ready we can go back to our program.
Let's create an instance of our HTP cooking or Kuki it calls we a little bit Googie we can
store a
key value pair using the indexer.
So Kuki of name it calls Marsch So name is the key and Marsha's the value.
And we can read that from the cooking.
So Consolo right line Kuki of name.
That's what the application.
So the cookie is working.
Now let's get back to a city cooking class.
We might be wondering why did we create an a city cookie as a wrapper around a dictionary
couldn't
we just go ahead and use that dictionary directly.
Well yes and no.
In this case in this simple example yes we could definitely just use a dictionary as an HD for
cooking
but an to be cookie is more than a dictionary for example.
It can have a property called expiry and that's the expiry date time or the cooking.
So we can go here and create an auto implemented property for that.
So Propp remember that tap that's a code snippet date time
expiry cookie can have other properties or methods and now it's more than just dictionary.
Internally it uses a dictionary for data storage.
So the takeaway from this lesson is if we're working with a class that has the semantic of a
collection
or a list or a dictionary we can improve wer code by declaring an index or and indexer is an
easier
way to access elements in that collection as opposed to having two methods like here if we
didn't have
this index or we had to create a method like public Floyd said item string key string value.
And we also had to create another method like public string get either string.
Keith there's nothing wrong with this approach but it's more efficient to just use an index or
both
in terms of the code in the class here as well as the code that we wrote in the consumer here.
OK that's it for this lecture.
I hope we enjoyed it and thank we for watching

Okay in the last section we learned about classes in this action we're going to talk about class
coupling
what is carpooling and suffering engineering.
Coupling is a measure of how interconnected classes and subsystems are at the beginning of
this course
.
I explained that a software application is composed of many classes that are package inside
various
named spaces and assemblies.
In this picture we have the classes inside an application.
I assume that we need to make a change in class A now Class B and Class F are both
dependent on Class
8 which means if a changes B and F may have to be changed or at least they need to be
recompiled and
redeploy it so that changing a may effect be an F as we see here but also Class D and Class C
are dependent
on Class B.
Similarly class she is dependent on Class F which means changing class A has a bigger
impact on our
application.
And again we see here.
Class E is dependent on Class D and class H is dependent on Class G.
So a change in class a a fixed even more of an application.
This is an example of tightly coupled design.
So an application whose classes are tightly related are dependent on each other.
It's considered to be tightly coupled application.
And this is very bad because there is a chance that we may break things along the way.
As a result of all these changes in the application in contrast to tight coupling we have a loose
coupling
so in this picture I'm demonstrating the concept of loose coupling between classes using a dot
to the
arrow.
And this is the ideal Soffer we want to minimize changes in our application.
So when we change a class we want that change to be isolated.
We don't want that change to affect other parts of the application.
Now we might ask what how do we design a Loosli couple of application.
Well there are three things we need to understand.
The first one is encapsulation which I explored in the last section.
Remember I talked about the restaurant in a restaurant.
We have various concepts like a manager and like a cashier a waiter waitress as Chef kitchen
hands a
waitress does not go to the kitchen and tell the chef how he should chop the vegetables and
how he should
cook.
That's the responsibility of the chef.
So the chef has some knowledge and some capabilities.
And if we want to model the concept of chef in software we want to encapsulate all those
concepts
in a class.
So no class from anywhere else in the application knows about details of how things are done
in that
class.
And we saw how we could use access modifiers to achieve that.
Now the next thing we need to understand is the relationship between classes which is the
topic of
the section.
And finally we need to understand interfaces interfaces are extremely important and they help
we design
Loosli couple applications.
That's why I have dedicated a separate section to interfaces so let's start with the relationships
in
general we have two types of relationships between classes.
We have inheritance and composition.
So over the next couple of lectures I'm going to talk about inheritance and composition both
in terms
of theory and practice.
And finally I'll talk about the concept of favorite composition over inheritance composition
relationships
usually result in less coupling.
And that's the meaning of this concept to favor composition over inheritance.
So let's get started.

OK inheritance in this lecture I'm going to tell we what is inheritance and why we use it then
I'm
going to show we an example of inheritance using UML notation we stands for unified
modeling language
and it's a graphical language for representing classes and their collaboration.
And finally I will show we the syntax of inheritance in C sure and then we'll do some coding.
So let's get started.
What is the inheritance.
Inheritance is simply a kind of relationship between two classes that allows one to inherit
code from
the other is usually referred to as ease a relationship.
For example we can say a car is a vehicle with inheritance we get code reuse.
That means being capture that some common code in one class and then reuse that in other
classes.
Inheritance also provides polymorphic behavior which is extremely powerful but it's beyond
the scope
of the section.
There is a separate section in this course called polymorphism and that's where we will learn
about
polymorphic behavior.
46 And let's just see how we can use inheritance to get code reuse.
Imagine we want to design an application like PowerPoint here.
I'm using keynote on Mac which is similar to PowerPoint on Windows.
So on this slide we can have objects like a shape text table and an image.
All these objects have some common attributes.
For example they have a with height and in position they also have some common behavior.
For example if I right click on this shape here we'll see Ring to front Santa's back cut copy
duplicate
and so on.
If our job is to develop an application like PowerPoint or keynote we can create classes for
each of
these objects.
For example we can have a class called Shape we can have a class called takes a class called
Table and
a class called image.
Now we don't want to duplicate all these common behavior and attributes in all these classes
so that's
where we can use inheritance to write code once and we use it in multiple contexts.
Here is the UML representation of the candy the classes for our PowerPoint application.
So I had a high level we can have a presentation object class which is where we encapsulate
those common
behavior and attributes then we can have classes like takes table an image which inherits
from presentation
object.
In this example we referred to presentation object as a parent or a base class.
Some people also refer to it as a superclass text table and image are referred to as child
derived or
subclasses in terms of syntax.
Here is how we implement inheritance in C-sharp.
So here we simply create our common class which is presentation of objects.
And then we create a new class like text that inherits from that we implement inheritance by
simply
appending a colon and the name of the base class after declaration of the trial class.
OK now let's start coding and see this concept in action.
OK let's start by creating a class called presentation object.
This class is going to be the parent or base of other classes.
So public class presentation object.
And here we can define a couple of properties like width and height
and a couple of methods like copy and duplicate.
I'm going to leave the implementation very easy so we just simply output a message on the
console So console
dot write line object.
Copy it to clipboard
object was duplicated.
Now let's put this class in a separate file.
So back here with resharpen alternate enter and enter.
Done.
Now back to our program.
Yes.
Let's create a new class that derives from presentation object.
For example text presentation object.
So this is the inheritance notation we just put a colon here and the name of the base class.
Note that in C-sharp a class can have only one parent.
Now let us define a few properties or methods that are specific to the text class.
So for example font size or font name
and maybe a method to add a hyperlink to a text or add hyperlink string here.
Now we mean to argue that we may need this feature on every presentation object and that's
perfectly
valid.
But for the sake of this example let's just add this method here because I want to demonstrate
the difference
between a parent and a child class.
So simply cancel and write line.
We added a link to.
Plus we are ok to clean up our code.
We go here and put this in a separate file.
OK let's go back to our program that C-s here.
I would like to create an object of type text so vortex it calls new text.
Now we type text dot.
OK here as we see we have members that are defined into takes class itself like the hyperlink
font
name font size but we also have members that we inherited from the parent class which is
presentation
object that includes copy method.
Duplicate method height and with properties.
We also have a few methods that we define.
In neither the presentation object nor the text class that includes the equals method.
Here are good hash code or get type or two strings.
These methods are defined in the object class which is the parent of all classes in dot net.
So when we create a class even if we don't specify the object class as its parent it
automatically
inherits the members defined in the object class or cover the object class in more details.
When we get to the section about inheritance but what I want we to take away from this
lecture is that
we added some common functionality in the presentation object class that includes a couple
of properties
like width and height and two methods like copy and duplicate and we inherited all this code
in the
takes class.
Using inheritance knownas go back to program that C-s and finish up this task.
So text dot with a 100th hundredth textiles copy.
Let's run the application.
So we got the message object copy to clipboard and the implementation of that was in the
parents class
.
Again I'll convert inheritance in more details in the section called inheritance for this section.
All I wanted to take away is that inheritance is a kind of relationship or association between
classes
and it has two benefits.
One is code reuse.
Another one is polymorphic behavior which we'll learn about soon.
I hope we enjoyed this lecture and thank we for watching

OK we got to composition in this lecture I'm going to talk about what is composition and
what are its
benefits then I'll show we how to represent composition using UML notation.
And finally I will show we how to achieve that in code.
So composition just like inheritance is another kind of relationship between two classes that
allows
one to contain the other.
We referred to composition as has a relationship.
For example we can say car has an engine just like inheritance with composition.
We get code reuse but composition is more flexible and it's a means to designing loosely
coupled applications
as we learn later in section as an example.
Imagine we're designing an application and as part of that we need to have a class called DB
migrator
that is responsible for migrating our database.
This class will be responsible for creating new tables populating them with data.
Maybe renaming columns dropping columns and stuff like that as part of that.
It requires some logging.
Perhaps we need to log each step in a text file.
Also in our application somewhere else we could have another class called installer which is
going to
be responsible for installing our application in a target environment just like DB migrator our
installer
also requires logging.
So as we see logging is something that is common between these two classes.
What we can do in this case is to create a class called logger that is responsible for logging
information
to a text file.
Here is a UML representation of this concept.
So here the Logger class has the capability to log messages in a text file.
DB migrator and installer.
They both have a relationship or association to the lower class.
The type of relationship is composition as indicated by black diamond on the left side of the
relationship
in C-sharp terms.
Composition is nothing new.
So if we want to implement what we saw in the previous diagram would simply create an
installer class
which has a private field called logger in the constructor of the installer class.
We get a logger object which we use to initialize that private field.
So for composition we don't have any special syntax like inheritance.
The related class is simply a private field in the composite class.
Now just jump into code and see the concepts in action.
OK we started by creating our Logger class which is where we have the common
functionality.
So
I'm going to keep this class as simple as possible because what we want to learn in this
section is
about relationship or association between classes.
We don't want to get distracted by details such as how to open a file to close it how to write
information
to a file.
So let's just leave that for now.
So I'm just going to create a method called log that takes a message and simply writes that to
the console
.
Now let's put this class in a separate file so alt and enter and enter back with control and
minus.
We create a new class called DB migrate for this class is going to be responsible for
migrating our
database so we create a constructor c tor tab.
There we go.
Now here we need a parameter of type logger we want to create an association to the Logger
class.
So longer longer.
I know it resharpen I can't put the cursor on this parameter here and simply press alt and enter
and
look the first item is introduce and initialize a field logger So enter it automatically created a
private
read only field as we see here and initialized it using the argument passed in the constructor.
Now let's say this class has a method like my great public void migrate and as part of
migrating which
is going to be a complex task we need to do some logging.
So all we need to do is to call the log method of the Logger class so logger that log we are
migrating
.
Blah blah blah.
Now we put this in a separate file.
We get back to program not see as using control minus.
Let's create another class call installer and we do the same technique there.
So we create a constructor ctor tab create a parameter here.
Longer longer Altan enter and enter again.
There we go.
We got the private field and get the method here.
Call it install again as part of installing the application.
Are going to log messages to our logfile.
So we simply call the logging method off the Logger class so we are installing the
application.
Now I'll just put this in a separate file to clean up our code to program dot cs.
OK now we create a DB migrator or DB migrator equals new DB migrator.
Here we need to pass a longer object.
So one way to do it is just to create another object here like new logger.
Another way is to declare a variable and assign it to the new logger and then we can pass that
variable
to the DB migratory constructor.
Let me show we this technique when creating a new installer.
So var logger it calls new logger.
Now let's create an installer var installer acost new installer.
So here again we need to pass a logger object.
So I'm just going to pass this logger object here.
Now let's call DB migrator dot migrate and installer dot install We run the application.
So here are the messages that are supposed to appear in our log.
So the interesting thing here is we declared that common functionality which was about
logging in a
separate class here and then we reused that into other classes using composition.
So as we have seen so far we have two ways to reuse code.
One is inheritance and one is composition.
They both are valid approaches but which one we use depends on the project we're working
on and its
requirements.
Generally speaking inheritance results in a more tightly coupled relationship with
composition we can
get loose coupling Plus more flexibility.
And that's the reason a lot of developers say faver composition over inheritance in the next
nature
.
I'll cover this concept in more details.
I hope we enjoyed this lecture and thank we for watching.

In the last couple of lectures we learned about inheritance and composition in this lecture I'm
going
to talk about problems with inheritance and then I'll explain that vantages of composition
over inheritance
before we start.
Let's review what we learned in the last couple of lectures.
So we saw that with inheritance we can get code reuse.
I showed we an example of a presentation object where we wrote some common code that
was inherited
by text table and image classes.
We also saw an example of code reuse using composition.
So we had a longer class where we defined the logging capability and then we use that class
in DB migrator
an installer.
Now the problem with inheritance is that it can easily be abused by amateur designers and
developers
which can easily lead to large a hierarchy of classes such hierarchies are fragile.
If we change a class on top of the hierarchy all the classes inherited from that will be
affected.
And this is because of the tight coupling that comes with inheritance.
Let me share an example.
So we can see all these problems in practice.
Imagine we are designing a game and we would like to introduce the concept of a person and
a dog Both
person and dog classes can have attributes such as age and they can have methods such as eat
and sleep
.
So we inheritance we can create an Animal class and then derive person and dog from the
animal.
Now let's see if we need to give the person and dog the capability to walk.
So we need to go in our Animal class and change that class by adding a new method called
Walk.
The problem at this stage is because boules person and dog derive from animal.
They will be affected as a result of this change.
Sometimes when we change a class the dependent class may have to be changed or at least it
has to be
recompiled and redeploy it.
OK now to make the matter worse.
Let's imagine we would like to introduce the concept of goldfish so we add a new class called
goldfish
that derives from animal.
But there is a problem here.
The problem is that the goldfish cannot walk.
So our inheritance hierarchy needs to be modified which means we have to take that walk
method outside
the Animal class and probably create another subclass called mammal where it has the
capability to walk
and then we can derive person and dog from mammal.
So as we see the hierarchy is getting changed again.
So that's the reason inheritance can easily be abused by amateur designers and developers and
it results
in large hierarchies and such hierarchies are fragile because of the tight coupling between
classes
.
Now I want to show we something I want to show we that any inheritance relationship can be
translated
to a composition and that can result in great flexibility.
So let's review the same problem and see how we can model these classes using composition.
So this time instead of person and dog deriving from animal they have an animal.
Now the first thing that may confuse we here is that a person conceptually is an animal.
At least that's how we define the concept of person in the English language.
Well that's exactly where the problem happens with inheritance.
Most amateur designers try to most offer using real world just because in the real world a
person is
an animal doesn't mean we should always use the inheritance or is a relationship between
these two classes
.
We as software engineers need to think differently.
We need to design our classes such that a change in a class is isolated and has minimal
impact on other
classes in the system and doing so requires a different way of thinking not the way that we
think in
the real world.
We basically need to think in objects.
OK back to our example.
Let's say we forgot to give the person and dog the ability to walk.
Now how can we model dogs using composition.
Well first we introduce a new class called walkable which has a method called walk these
walkable class
describes the behavior of walking for any kind of animal.
Next we create a composition between person and walkable.
Same for the dog.
Now what happens here is that a person has an animal.
And it also has a walker.
So he has the capabilities defined in both the animal and walkable.
Now Nancy we would like to add a goldfish.
So we create a new class called goldfish that is composed of animal goldfish cannot walk.
So we are not going to create an association or relationship between goldfish and walkable.
Know that in the example with inheritance I think the goldfish class broke the hierarchy.
But here we simply added the new goldfish and created the composition between goldfish
and animal person
is not modified dog is not modified animal is not modified neither is walkable.
Now let's say we would like to give our goldfish the ability to swim so we can create a new
class called
swimmable which has a method called swim and then we create a composition association
between goldfish
and swimmable.
Again none of the classes in the system have been modified.
Tomorrow we can introduce a new class called duck.
A duck is an animal.
It can walk and it can swim.
So again we can create the composition between dog animal walkable and swimmable
without any impact
on person dog and goldfish.
So as we see with composition we encapsulate some common functionality and then we
compose them together
.
We tied them together to create new classes using this technique we can create new classes
with new
capabilities of the existing classes we compose them together.
And this has minimal or zero impact on other classes.
So with composition we get great flexibility but we also get loose coupling.
How.
Let's take a look at both the composition and inheritance relationships in terms of coupling.
So here in this picture we have both an example of inheritance and composition.
In this example coupling between person and animal irrespective of the kind of relationship is
equal
.
So whether we use inheritance or composition if animal is changed person may have to be
changed or at
least needs to be recompiled and redeployed.
But there is a catch here with composition.
We get an extra benefit which is not possible with inheritance.
And that is we can replace the Animal class on the right side within the interface.
Interfaces are extremely powerful and that's the reason I I've dedicated a full section on them
for
this lecture.
Don't worry about it.
All I want we to take away from this lecture is that we have two types of relationships
between classes
.
One is inheritance which is also referred to as is a relationship.
And another one is composition which is referred to as has a relationship both inheritance and
composition
have pros and cons inheritance provides code reuse and is easier to understand then
composition in certain
examples.
For instance in the example we saw earlier we usually think a person is an animal.
So modeling that using composition like person has an animal is a little bit harder to
understand but
the bad thing about inheritance is that it creates tight coupling.
It can easily be abused and result in large hierarchies which are fragile and simple change and
propagate
to many parts of the application and that change can be very costly composition on the other
side provides
great flexibility and loose coupling but it's a little bit harder to understand.
In some cases Now I'm not telling we that inheritance is necessarily a bad thing.
In fact all inheritance and composition are great techniques but we need to use them
appropriately
.
What I wanted to take from this lecture is just because in the real world we think of a lot of
relationships
as inheritance or ease a relationship doesn't mean we need to model them the same way in
software because
again doing so can easily result in large hierarchies with many levels of inheritance.
That's it for this lecture.
I hope we enjoy it and thank we for watching

OK we got to access modifiers earlier in this course we learn about access modifiers.
We learn about public and private.
And this lecture I'm going to explain access modifiers in more detail I'm going to talk about
why access
modifiers are important and to explain that I'm going to use the blackbox metaphor.
And finally we get into C-Sharp access modifiers So let's get started.
A metaphor often used in object oriented programming is blackbox.
Look at this black box image here.
We didn't know what's inside this box.
There is limited visibility and there is just one I don't know if it's a button or a light and that's
all we can see.
We want to design our objects to look like a black box.
So there is limited visibility from the outside but it could be a lot of magic going on inside.
Now we may wonder why do we want to design our classes like a blackbox.
It all comes back to isolating changes.
The more A-class reveals about its internals or its implementation the more risky it becomes.
When we are going to change that class because there could be other parts of the system that
rely on
that implementation.
So we want to limit the visibility from the outside and make our class look like a black box.
Here's another metaphor look at this DVD player always see from the outside.
It's just a few buttons and an indicator but there's a lot of complexity inside that DVD player.
There is an electronic board with a lot of eyes sees and who knows there's a lot of complexity
there
.
What we see from the outside is called public interface.
Again we want to design our class to look like this DVD player.
So it's public interface should be very simple.
Now in C-sharp we use access modifiers to control visibility to members of a class.
We have all seen public and private.
But we also have protected internal and protected internal Let's explore these access
modifiers in detail
and memory that is declared with public is accessible from everywhere.
So in this example we have a customer class with a method that is declared as public.
With that we can create a customer object somewhere else in the code and call the promoter
method the
promote method.
It's going to be visible to the outside.
That's perfectly fine because promote should be part of public interface of the customer class.
It's all about implementation.
We may want to promote a customer and that's unexpected functionality.
Now private is the complete opposite of public.
So a member that is declared as private is only accessible from that class.
In this example in our customer object I have a method called calculate rating.
We're going to use this method as part of promoting.
So perhaps we need to do some calculation and based on the result of that.
We may promote a customer to a certain level.
This is about implementation detail.
It's about the internals of the customer class how we promote a customer.
We don't want to classes to know anything about that.
So that's an example where we can use the private modifier to limit access to this method.
So as we see an example if we create a customer object we are not going to be able to call the
calculate
rating method.
It's not going to be compliant.
OK next is protected and membered declared as protected is accessible only from the class
and it's derived
classes.
What does it mean.
Well look at our calculate rating method again here.
This time I declared it as protected instead of prime.
So this statement says accessible only from the class and its derived classes which means
outside the
class if we have a customer object we're not going to be able to call this method.
So it's a little bit similar to private.
The difference is if we derive a class from customer let's call it gold customer.
That method is going to be visible in a derived class.
Now there is a problem here.
The problem is as we explained in the last slide calculate rating is about the implementation
detail
which should be encapsulated inside the customer class itself.
We don't want it anywhere else in the code.
We know about this method because we may change it in the future.
We may rename it we may change its parameters or we may even remove it.
We don't want anywhere else in the codebase and a dependency to dismiss it.
Now the problem with the protected modifier is any classes derive from this class.
We'll still be able to see this method and that breaks encapsulation because as I have
explained throughout
this course encapsulation is about hiding the details inside the class and only revealing the
minimal
that is the public interface of a class.
So a lot of developers consider protected a bad design in the C-sharp language.
Having said that we will see a lot of places in the Dathan framework or in many other
libraries where
protected is used.
Now to make all this easier for we.
What I'm suggesting is avoided if we can and prefer to use private methods.
But if there are circumstances that we have to use protected and we have a valid reason for
that that's
OK go ahead and use it.
Just be aware that we're revealing the implementation detail of a class any of its subclasses
which
can be trouble in the future.
OK next one is internal internal is a modifier that we often use with the classes not their
members
.
It really doesn't make sense to declare a class member as internal but there are cases that we
may
declare a class as internal For example continuing from our last example imagine we have a
separate
class called Race calculator and race calculator might have a bunch of methods and some
complex logic
to calculate the rate for our customer.
Now this class is part of the implementation detail for the domain of customers.
So inside that domain it's OK for every other class to see this class.
But outside that domain we don't want anyone else to know about the existence of this class.
So how we implement that in C-sharp terms is we create a separate class library.
And in that class library we declare the race calculator class as internal.
So inside that assembly or that class library everywhere we will see this class.
But outside that assembly no one knows about this class.
Again I'm going to show we all of this stuff in the code.
So if that sounds unfamiliar don't worry about it.
And finally we've got protected internal which I would say is the most major thing in our
language.
Basically what it means is a member declared as protected internal is accessible only from the
same
assembly.
And that's because of internal or any derived classes.
And that's the result of protected.
So here's an example.
We have a customer class and it has a method called weirdo that is declared as protected
internal.
Now this is really bad both in terms of teaching learning writing code and someone reading
that code
.
It takes a lot of brainpower to understand what's going on.
I decided that in this lecture because I want my course to be comprehensive but it's very
unlikely that
we're ever going to need it.
OK.
Let's start coding and see all this access modifiers in action.
OK let's start by creating a customer class so public class customer can define a couple of
properties
like ID and name
on a method like promote.
Now let's go to the main method and create a new instance of customer Savar customer and
he calls new
customer.
Now if he type customer dot eeriest the public interface of this customer class.
So we have a few methods like equals get hash code get type 2 string which are derived from
the base
object class.
And we also have these bold members here that are defined in the Customer class itself.
So Id name properties and the promote method.
All of these together make up the public interface of the customer class.
Now back to the black box metaphor or the DVD player we want to minimize this public
interface the more
we've revealed about the class and its members the more we raise that other parts of the code
will be
dependent on those members.
So this creates more coupling which means if are going to change the implementation of our
customer
class auto parts of the code make it broken.
Let me show we how this happens.
So I'm just going to remove this.
Let's create another method.
We are going to calculate the rating of a customer.
So just public and calculate rating.
I'm going to leave out the implementation of business logic here and just return a simple
number because
we don't want to get distracted with some business rules and whatnot.
What I want to show we is in the promo method perhaps there is a call to is calculate rating
so we
can say we're rating equals calculate rating and then based on what is returned from that
method we
can make decisions.
For example if rating is whatever then console dot write line promoted to level 1 otherwise
promoted
to level 2 just keeping it simple.
Now the problem here is this method is about implementation detail of the customer class
from the outside
.
We don't really need to see this method.
What the consumers of this customer class need to see is just this couple of properties here
and to
promote Mitha how to promote method does its job which in this case means calling that
calculate rating
is no one's business.
So this is what encapsulation means.
We're just going to hide details inside and reveal the public interface.
Now the problem happens if somewhere else in the code we out of interest or curiosity of a
call to calculate
rating method
now because this is the implementation detail of the customer class tomorrow we may decide
to change
it.
For example when we decide to pass a parameter like a switch say exclude orders it might
have some meaning
in the business domain we're working on.
So we're changing this method.
And what happens is the we get this red underline here.
Now if this method is being used outside this class like in this case in our main method here
the code
is going to break.
And imagine if there were 10 other places in the code where we made a call to this method.
But in this case if this method was declared as private in the first place nowhere else we had a
call
to this method and fixing that change would be as simple as just making a change in one
place in the
code which is to promote method that is using this calculate rating method.
So here I would say exclude orders.
True but this is the reason we want to minimize the public interface of a class to the outside
world
.
Now let's get rid of this calculate rating method here.
OK.
Now let's put this customer class in a separate file to clean up our code.
So alternate enter enter.
Now back to program.
This creates a class that derives from the customer class so that we call a gold customer
and the customer here.
OK here we can have a method like offer a voucher.
So let's say we're going to give a voucher to our gold customers.
So public FOID offer voucher.
And of course this method needs some argument like a voucher object.
But again to keep things simple let's not worry about the prompter.
What I want to show we is inside this method if we use this dot.
So these are the members that we see in this class.
So he calls get hash code get type member wise clone and to a string where derived from the
base object
class.
That is the parent of every class and dot net id name and promote are derived from the
customer class
itself and offer a voucher which is indicated by bulled is declared in this class itself.
So as we see calculate rating method it's not visible here because we declared that as private.
So back to Customer class look Ganguly rating is declared as private.
And my rationale was because this is the implementation detail we want to encapsulate it.
We don't want anywhere else in the code to have dependency to this method.
Now if we changed it to protect it
and go back to our gold customer class.
Look this does.
And here we see the calculate rating method.
And here's the problem.
We created a dependency to the implementation detail of the customer class.
So again if tomorrow we're going to change that Mitha maybe we rename it maybe we add a
parameter or
maybe we even delete that method gold customer class.
It's going to be affected.
Let me show we this in action.
So imagine as part of offering voucher we're going to call this method and let's pass whatever
switch
here and get a rating here.
And based on that rating we're going to do some logic.
Now if tomorrow we go to the customer class
and decide to totally drop this method maybe our business logic or promoting a customer is
changed.
So I'm just going to remove this method and let's say I'm going to change the logic of
promote method
that promote logic change.
Now see what happens in the gold customer class.
So the calculate rating method does not exist anymore because we deleted it from the parent.
Again here is where encapsulation is broken.
So try to avoid protected unless we have a valid reason to use it.
For example if we know that the concept of calculate rating is completely stable in the
business too
many have been working on it it's OK to use that.
Also as I said there are some design patterns that use protected methods as part of their
implementation
.
OK let's move on and see the internal modifier.
So I'm going to just remove this class
ok to see the internal in action we need to move our customer class to a separate assembly.
So what I'm going to do is right click on the solution go to I'd actually we're never going to
see
that in the screencast.
So I just drag and drop the solution explorer to the left so we can see right click on the
solution
.
I had new project and we select class library.
So with a class library we create DL L are dynamically linked library and we can reference
that in various
applications.
So give it a name.
Let's say we're building an application for Amazon.
So.
So I'm going to call this class library Amazon
no by default we have class 1 in this project this class library I'm going to remove that
and then I move this customer in class inside the Amazon class library.
Yes.
When we open it know that here we have the old namespace.
So we need to change that because now the customer class is inside the Amazon project.
So with resharpened this is pretty easy.
We just put the cursor here and Polton enter the first item says move declarations to
namespace Amazon
enter down.
So here in this project we're going to implement our business logic.
We have the customer class and we also are going to create a new class for calculating rating
of the
customer.
So a public class rate calculator and it could have a bunch of methods and properties and
fields.
I'm just going to keep it simple.
So let's have a method called calculate which gets the customer object.
And for simplicity let's just return zero in the promote method of our customer.
I'm going to make a call to this calculator.
So our calculator goes new calculator.
We rate calculator and rating equals calculator dobbed calculate and I pass this as the object
as the
customer object to that method.
And based on that rating we can do some conditional statements and decide how to promote
the customer
.
I need to add a caveat here.
Generally speaking it's not a good practice to instantiate a new object like the race calculator
inside
the method here because this creates coupling or dependency to this object.
When we get to the section about interfaces we show we a better way to implement this code
or no let's
just move on.
So let's recap.
First of all I'm going to put this class in a separate file.
So alternate enter and enter again.
All right let's recap.
We have Amazon class library which is going to be our DSL.
We two classes customer and race calculator.
Rachel peculier simply has a calculator method and returns 0 in the Customer class as part of
promoting
.
We use the calculator object to calculate the rating.
Now let's clean this up.
Back to our program here we have the customer object right.
I just notice a problem here that when we copy it when we drag and dropped the customer
object from
X is my first project inside Amazon.
It was not deleted from the source.
I think I made a mistake while recording.
So I'm just going to delete this class.
All right.
Now in our program which is in the access money far as the customer is not detected.
So we put the cursor here and resharpen has this red icon here if we press alt and into it we
can activate
that.
So I was suggesting to reference Amazon what it does is it goes to the references folder and
as a reference
to Amazon.
If we don't have any sharper what we need to do is still at that and delete the using statement
on the top
.
So see the customer class is not detects it.
We simply right click on references either reference then expand solution.
So in our solution we have another project called Amazon I select that and click OK.
So now we have a reference to that assembly that class library and we can use any obvious
classes.
I know to use the customer.
We simply go on the top type using Amazon because that's the name space.
So we see with resharpen it's much easier.
We don't have to do all these manual steps.
All right let's move on now.
Let me show we that in the main message here.
If we type Amazon which is the name space dot we see two classes customer and race
calculator.
In this case race calculator is used as part of promoting a customer so we can argue that it's
the internals
of the customer or the Amazon domain.
And based on the capture lation principle of object oriented programming we shouldn't reveal
the implementation
anywhere in the code.
So the problem is if we use this rate calculator here calculator.
Now these projects are access modifiers.
Is program class in the main method.
We have a dependency to this calculator object.
In the future if we go to our Amazon class library and decide to get rid of this red calculator
let's
remove this class here.
The areas that are affected.
One is inside the customer class here.
But we also have this line in so many holes in the code that is broken.
And that is not good because this way we could have 10 other places in the code where there
is a dependency
the rate calculator which is about implementation.
If it declared this rate calculator as internal It would have been visible inside this class library
here but not anywhere else in the code.
So let me add that rate calculator back here.
So I have a new class rate calculator
and put that calculator method back calculate return zero.
Now this summer declared as internal.
What happens is in the Customer class this class is visible because he's part of the same
assembly but
the outer disassembly when we go to access modifiers we cannot access this class.
The red underline it says can love access internal class rate calculator here.
Well that's pretty much for this lecture.
I hope we enjoy it.
And thank we for watching

OK earlier in this course in the section about classes we learn about constructor's in this
lecture
we're going to learn more about constructors and inheritance.
There are two things we need to know about constructors when it comes to inheritance.
First is that during the instantiation of an object the base class constructors are always
executed
first and the second is base class constructors are not inherited.
So in a derived class we need to redefine wer constructors.
It's easier to explain these with an example.
So here we have a vehicle class with a private field called registration number the vehicle
class has
a constructor that takes a parameter of type string called registration number and we use this
argument
to initialize the private field here.
Now let's say we would like to create a class that derives from be called.
So our class can look like this.
The core class that derives from Mieko know that I have redefined a constructor with a string
parameter
for the registration number here.
The reason for that is even though we define a constructor in the vehicle class.
It's not going to be inherited by the car class.
So we need to redefine the constructor here.
But what are we going to write in this constructor.
Well I've highlighted this line with red which means this is not valid.
In fact if we read this code it's not going to be compiled.
We're going to get an error.
Why.
Because in the vehicle class we declared registration number as private.
Let's take a look at the vehicle class again.
So note that the registration number is declared as private which means it's not going to be
accessible
in the current class and in the lecture about access modifiers.
I explained why private is a better choice than Protector's.
So back to our car class at this point we are not going to be able to access the registration
number
field because it's the implementation detail of the base class which is vehicle which we would
like
to encapsulate in the vehicle class itself.
So that detail is not leaked anywhere else in our program.
No instead if it declared that as protected just let's say for argument's sake we would be able
to access
that field here.
But still it's not a good idea to initialize that field here because we define this concept
somewhere
else in the code in the vehicle class's constructor.
So we should not repeat ourself.
Instead what we need to do here is to reuse that code we wrote in the vehicle classes
constructor how
we do that is using the base keyword.
So all we need to do here is when declaring the constructor for the car class before opening
the body
of the method here we up and colon base and here base is simply a way to access the base
class.
The syntax simply represents a method call.
Imagine we're calling a method called base.
And here we're passing an argument to that method.
That method is simply the constructor of the vehicle class.
So the constructor of the car class receives an argument called registration number.
And here we simply pass it to the base classes constructor and in the constructor of the car
class here
we should write anything specific to the initialization of the car class itself.
OK.
Now let's start coding and see this concept in action.
OK I'm going to show we a few different things here.
First let's start by creating a vehicle class so public class recall list creates a default or
parameterless
constructor.
So a seat or tab.
And here we use console that writes line to log a message to the console.
So CW type vehicle is being initialized.
Now those define a car class that derives from the call.
And again here define a constructor that simply logs a message to the console.
So ctor tab console dot write line car is being an issue.
Licet OK.
Now to clean up our code we put these classes in separate files.
So we go here Polton enter enter control minus back here
again one more time back to program.
Now here we create a core object Savar car equals new car.
There we go.
Let's run this application.
Note that we got two messages on the console.
First Monday's vehicle is being initialized and the second one is car is being initialized.
So what we see here is when we create an object the constructor of the base class is always
executed
first.
OK now let's extend this example and take a look at the base keyword.
B go back to our vehicle class.
So I'm going to leave this default constructor here but I'm also going to create another
constructor
that takes a parameter called registration number.
So ctor tab.
This one is going to take we parameters so String registration number.
And here we can use Altan enter.
And the first item is introduced and initialize field registration number.
And as we see what happens is resharpen automatically creates a private Read-Only string
field called
registration number if we like this kind of fast coding techniques.
I have a course called Double wer coding speed where I teach we lots of techniques to write
code faster
and easier.
So Mac for example here the vehicle class has two constructors one is default or
parameterless and the
other one takes a parameter of type string.
Now let's go to our car class.
At this point everything is fine.
The reason for that is the vehicle class has a default or parameterless constructor.
So we can create an object of type car.
And at this point first the default or parameterless constructor of the vehicle is executed.
And then this constructor here will be executed.
But let's see what happens if we go to the Ricoh class and comments out this default
constructor.
Now back to our car class.
Look we got a red underline here and the error is saying based glass Veikko doesn't contain a
parameterless
constructor.
What does this mean.
Basically what's happening here is when we create an object of type car the runtime first tries
to create
an object of type vehicle but because the vehicle type does not have a default or prominences
constructor
the runtime doesn't know how to create an object of type recall.
So what we need to do here is back to the core class we use the base keyword to call one of
the constructors
of the vehicle class and how we do it is very simple.
Enter Colon.
We use the base keyword open brackets.
And here we go.
We have one constructor that takes a string prompter called registration number.
Now at this point we need to supply some value.
We can simply hard code something here but it's not a good idea because we don't want to
hard code and
registration number here.
A better way is to receive a parameter called registration number in the car class's
constructor.
So here string registration number and whatever we receive here we simply pass it to the base
class
.
There we go.
Now just modify the message belong on the console to see the order of execution in more
detail.
So what I'm going to do is I simply add the registration number here
registration number and we do a similar technique in the vehicle class's constructor
.
Vehicle is being initialized.
And here the prompter is going to be registration number.
Let's run the application again.
We had a builder and see what's happening here double click here.
Here the aerosolize car does not contain a constructor that takes 0 arguments.
So what's happening here is we change the constructor of the car class to receive an
argument.
But here we forgot to supply one.
So let's just add the registration number.
X why is that 1 2 3 4.
On that occasion again not that the vehicle is being initialized first and then the car is being
initialized
.
And in both constructors receive a parameter and that is what we passed here during
instantiation of
the car object.
Well that's pretty much it for this lecture.
I hope we enjoyed it and thank we for watching

Okay at this point we know how to use inheritance in C-sharp when we have a base and a
derived class
.
There are situations where we need to convert an object to a base or a derived class reference.
And that's what they're going to learn in this lecture.
So I'm going to talk about conversion from a derived class to a base class which is referred to
as upcast
think.
And then I'm going to talk about the opposites.
So from a base class to a derived class which is referred to as downcasting.
And finally I will explain that as in is key words.
So let's assume we have a class called shape on a classical circle that derives from the shape
to keep
things simple.
I have excluded the members of these classes in this example.
OK now let's talk about casting.
In this example we have an object called Circle which is of type circle as we see from this
example
in C-sharp we can convert an object like circle to its base class reference.
In this case shape no conversion is required.
So it's implicit.
And now let's look at downcasting.
So falling from our last example we can convert shape to a circle object using an explicit cast
as we
see in the example.
Now one thing we need to be cautious about is that casting can throw an invalid cast an
exception in
this example our shape object is actually pointing to a circle object and runtime.
So we can cast it to a circle but if we try to cast it to another type like a car it's going to throw
an exception.
So here is an example.
We cannot cast a shape to a car and that throws an invalid cast exception.
Now to prevent this from happening we can use the as keyword.
So imagine we have an object and we would like to convert it to a car with explicit cast as we
see
here.
We may get an exception a safer way is to use the as keyword so when we use the as
keyword.
If the object cannot be converted to the target type we are not going to get an exception.
Instead what is return will be no.
So in the next line we can check if the result is not known.
And then we can do whatever we want with that object.
We also have is key word with the key word we can check the type of an object.
So we can't say if an object is a car then we can safely cast it to the car.
Otherwise we want to any casting.
OK let's jump into cold and see all these concepts in action plus some real world examples of
where
we need to do conversion between objects.
OK.
We're going to see a few interesting and useful things in this with we.
Let's start by creating a class called Shape.
So the public class shape the intention here is to model an application like PowerPoint or
keynote on
Mac.
So we have the concept of shape which is going to be common across other concepts such as
text table
image whatever.
So each shape in our PowerPoint application is going to have at least width and height.
So we create two properties width and height and at least it needs a position so we can have
an x and
y.
We also need a method to draw a shape so public voyde draw to keep things simple.
I'm just going to leave out the implementation for now.
So let's move our shape glass to a different file just like we have done in other exercises.
Altan enter enter back with control and minus.
Now let's create a class called text that derives from shape.
Now are tigs class needs some additional properties like font name or font size so font size
and font
name
again we're going to move this class to a separate file.
So
back to our program.
Now let's create an object of type text
text text it calls new text
not want to show we of casting so we can declare a viable of type shape and simply assign it
to text
as we see.
No conversion is required.
So we can implicitly convert an object reference like text based class reference like shape.
And this is very powerful.
I'm going to show we how are going to use that in real world applications.
But before we get there let me tell we a little bit more about what is happening behind the
scene.
Both this text and shape objects are actually pointing to the same object in memory.
Well it's more accurate to say takes and shape are both references to the same object in
memory but
they have different views what it means is if I go here and say text dot I can see all the
properties
of a Takes object.
So font name font size plus the ones inherited from the base class.
But if we use the shape reference we see a more limited view.
So as we see font name and font size are not there even though at runtime the object that we
have in
memory does have those properties.
But we are not going to see them if we use the shape reference.
Now we might wonder why do we need a more limited view of an object.
We'll get there.
I'll explain that in a real war scenario.
But for now let's just do a simple experiment.
So what I'm going to do is first I use that takes object and set with two 200.
Now I use the shape reference and modified that with two hundred.
Finally I'm going to display the width of the text on the console console dot write line takes
that
with what value do we think we are going to get on the console hundred.
Because all text and shape are references to the same object.
They just have different views.
Let's run the application and verify this.
There we go.
So we got 100.
Now what's the point of converting an object reference to its base class reference.
Well this is actually very powerful.
And that brings us to a new topic called polymorphism which we're going to see in the next
section.
But for this video let me give we some insight about where we're going to use this kind of
conversion
in a real war scenario.
Well first of all let me clean up all this code here.
OK.
In Dathan framework we have a class called stream reader which we use to read data from
any stream of
any kind.
So let's create an object of type A stream reader so stream reader reader icles News Stream
reader.
OK.
That Here we have a few overloads or the constructor of this class.
The simplest one is the one that takes a stream object.
In the framework stream is the base or parent of every kind of a stream.
For example file a stream or memory Stream.
Let's take a look at them in the Object Browser.
So we go to View and then Object Browser
in the search box for this type file stream.
So here is our file stream class which is defined in system data.
Io namespace.
Here's the declaration of the file stream class.
Note that it derives from a stream.
And here are the members of the final string.
So we use a file a stream object to work with the file.
It has methods to read from a file or write to a file.
Now let's take a look at the memory stream.
So like here.
Search for memory stream
again here in the declaration of memory stream.
Note that it derives from Stream.
Now let's get back to our program
in practical terms.
In the constructor of a stream reader we can pass any object whose type we arrives from the
stream
class without any conversion.
So what we can do here is we can simply pass a new file the stream or we can pass a memory
stream.
So any class that derives from the stream class.
So back to our upcast in concept the object we're sent here will automatically be upcast to its
parent
class which is string.
Let's take a look at another example.
So I'm going to come at this out
we have a class called array list which we can use to stir objects in a list array list lists a cause
or a list or we could use var here to keep our code cleaner.
Now let's take a look at the Add method.
The method takes on an argument of type objects and remember objects is the parent of all
classes in
the docking framework.
So essentially what we can do here is we can't pass any object to this method and no
conversion is required
.
So I can either number here or I can add a string or I can add a text object and all of these
objects
will be implicitly converted to the base object class.
Now in real world applications we should not really use the Israeli's class because it's not a
typesafe
kind of list.
As we see we can store a different kind of object in every element.
So in this example the first element is a number.
The second one is in the string and the third one is a Takes object.
So at runtime we make exceptions as a result of converting array elements to target types.
A better way is to use generic lists so we can use a generic list class like.
Or let's call it another list it calls new list.
This is a generic class a generic class takes a parameter which is used to enforce some kind of
concentrates
on that class.
So for example if I put integer here my list is going to be a list of integers.
So every element in the list is going to be an integer.
Or we could use a list of shapes which means every element is going to be of type shape so
we can store
a shape object or an instance of any of we ref classes.
OK so that's all about upcast Singh.
Now let's take a look at downcasting.
So let's clean up all the code here.
I'm going to declare a shape object.
So shape shape.
I know I can assign it to a text.
So even though at compile time the type of our shape object here is shape at runtime its type
will be
text.
Let me show we what I mean by that.
So I put a breakpoint here using f 9.
I run the application in the debug mode using F5.
Now we press F 10.
OK here in the watch window.
Let's clean up whatever we had here.
So I just type shape.
So this is a way to watch objects and their content in C-sharp.
So as we see our shape object is actually a type text me when do I declare it as shape.
Now the problem with this shape object is if we type shape dot we get a limited view.
As I explained earlier.
So we're not going to be able to access the properties defined in the takes object.
So that's where we need to downcast the shape object.
So what I would do is I declare a text quoted text and I apply a cast here.
So I want to convert a shape to a text.
Now with this object we have access to every property in the takes class like fonts name or
font size
.
Now we might wonder what is a real world example of having to downcast optics.
Well to demonstrate that I'm going to close this project
and create a new project
I'm going to use WPA application.
Or we could use Windows form application.
Either of these are used to build desktop applications for Windows.
So let's go ahead with WPA application.
Leave the defaults in terms of name or location.
It doesn't really matter.
OK.
OK.
Here's our designer and as we see we have a blank form.
So if we run this application which is going to see a blank form.
There we go.
So just a blank form.
Let me close that.
Now what I want to do is to put a button on this form.
So from the toolbox find under common WPX controls.
Drag and drop button here.
Now double click that the designer creates a method here called a button underlined click.
This method will be executed when the user clicks on the button.
We can't just display a message here.
Message Box start to show Hello world.
Let's run the application.
So I click the button and we got this hello word message.
Right.
OK now let's take a look at the parameters of this method.
The first one is of type Object and he's the center or source of that click event.
In this case that's going to be a button.
But the problem is if I type sender dot I don't see any properties or methods related to the
button
class.
All I see are the members defined in the object class.
This is a very common case where we need to downcast and object.
So we can do a cast of button and store that in a separate variable like button.
And here we have access to all these properties and methods of the Button class there we go.
Now note that in this example because I was sure that this method is the click handler for a
button
it's safe to cast it to a button like this.
But if there are situations where wer downcasting an object and we're not sure about the
runtime type
of an object that's where we use the as keyword.
So alternatively we could do sender as button and then if Button is not know it we could have
any code
that requires to access a button object.
So at this point I know the conversion was successful and I can type BOTTEN dot actual
height.
Let's put we on the in a message box.
I would need to convert that to a string because actual height is a number and the show
method of the
message box requires a string.
So let's run this application and I click the button that we got.
Twenty one point ninety six.
OK I know we got the second message box which is the hello world.
OK.
Well that's pretty much it for this lecture.
What they want we to take away is in C-sharp of casting is place it.
So we can simply convert an object reference to its base class reference.
In practical terms that means wherever a method requires an object of a given type we can
pass an object
of that type or any types that derives from that type.
The second thing I want we to take away from this lecture is in situations like handling the
click
of a button or anywhere where in wer method will we get an argument and then the argument
gives we
a limited view to that object.
We can use downcasting to convert that object to a more specific type and to do that we can
use an
explicit cast or the ASCII word.
I hope we enjoyed this lecture and thank we for watching.

OK we go to boxing and unboxing and this video I'm going to talk about the concept of value
types and
reference types.
And from there relate to boxing and unboxing so all types and C-Sharp are divided into two
categories
value types and reference types
value types are stored on the stack.
What is this stack when wer program is executed a limited amount of space and the memory
is allocated
to each thread of wer program and this space is used to store simple values like all primitive
types
like Byte integer float char pool as well as the struct type values stored in the stack.
Have a short lifetime which means as soon as they go out of scope they immediately get
kicked off the
stack by the runtime.
We also have reference types reference types are stored in the heap which is a larger amount
of memory
.
We use Hieb to store objects that require a longer lifetime examples of reference types and C-
Sharp
are basically any classes.
So the object class that is the parent of all classes or the Array class or the String class or let's
say we have a custom class called DB migrated.
These are all examples of reference types.
Now why does it matter.
Well earlier in the section we learned that an object reference can be implicitly converted to a
base
class for reference.
And here's the example I showed we.
So here we create an instance of a Sirico class and then we can't simply assign it to a shape
reference
.
So this object reference can be implicitly converted to a base class reference.
No conversion is required.
We also learn that the object class is the base of all classes in the Dathan framework.
So taking the last example we can modify to something like this.
So since the object class is the base of all classes in the framework we can't simply pointed to
any
objects and that object reference will be implicitly converted to the object reference.
Now that brings us an interesting scenario where we put a value type.
On the right side of the assignment operator and this is what we call boxing.
So in a formal definition boxing is the process of converting a value type instance to an
object reference
.
So as an example here I have a number that is of type integer and since object is the base of
all classes
in the dominant framework we can declare an object variable and I assign it a value type as
we see
here.
Or a different way to write the same code.
It's like this.
We simply declare an object variable and I assign it the value.
What happens behind the scene is its value gets boxed by the CLR and stored in the heap
instead of the
stack.
So let's take a look at the memory visualization.
So assuming that here we have a stack and a heap and on the stack we have a variable called
number with
the value of 10.
Now when boxing happens C-L are creates an object in the heap and then creates a reference
in the stack
that points to that object.
So as we see the value is now stored in the heap along with an object reference in the stack
when boxing
is the opposite of boxing.
So in this example we have an object that is assigned 10.
So at this point boxing happens.
Now when we cast an object to an integer unboxing happens and the result is we get a new
variable on
the stack called number with a value of 10.
All we need to know about boxing and unboxing is that they both have a performance penalty
because
of that extra object creation.
And that's something we should avoid if possible it's best to show this with an example.
So let's start coding and see boxing and unboxing in action.
OK.
Earlier I told we about the elite class.
This create an object of type or at least
none that take a look at the method
as we see it the method takes an argument of type objects which means because the object
class is the
parent of all classes.
We can pass any objects here so I can pass a number here or a string or a date time
or anything.
Now there are two problems with the array list.
The first one is type safety as we see.
Each element here has a different type.
So we lose type safety which means at runtime if I try to get the second element of this list
and cast
into an integer we are going to get an exception.
So let's declare a variable called number and get the second argument of this list and cast it to
an
integer.
Now the second argument is of type string.
So if we do casting here we're going to get an invalid cast exception.
So that's one problem with the array list but there is another problem.
The problem is the add method takes an argument of type Object which means if we set a
value type here
boxing will happen and subsequently when we get that value back and cast it on boxing
happens.
So in this example one is an integer.
It's a value type.
And here we get boxing.
String is a reference.
And in this case boxing is not going to happen.
And daytime is a structure as we see here.
The structure is also evaluated.
So here boxing happens.
Another way is to use a generic list.
So instead let's create another list and use the generic list here and let's say we want to store a
list of numbers so we pass integer as a generic parameter is generic list class is defined in
system
that collection is the generic namespace.
And now let's take a look at the method.
So another list at look it receives an argument of type integer as opposed to object.
So we get type safety which means every element is going to be an integer and no boxing will
happen
because internally this list stores a list of integers not a list of objects.
Let me show we another example.
So this time I create a list of names and I use a generic list of strength.
Now if we access the adman's that every element is a string.
Again we have type safety and no boxing.
So the lesson here is when we're working with a class if we're calling a method and that
method gets
an argument of type Object be aware that if we pass a value type there boxing is going to
happen.
And this has a performance penalty.
It's better to use a generic implementation of that class if it exists.
Well that's pretty much all we need to know about boxing and unboxing.
I hope we enjoy this lecture.
And thank we for watching
OK we go to method over writing and this lecture I'm going to talk about what is method
overriding and
introduce we to two powerful keywords in C-sharp called Virtual and overwrite method or
rightthing
is simply modifying the implementation of an inherited method.
What does it mean when we use inheritance.
There are times that we may want to modify the implementation of a method that we
inherited from a base
class.
Maybe that implementation doesn't apply to a derived class.
That's where we can use method overwriting.
So we override the implementation of an inherited method.
Sometimes developers need to get confused between method overriding vs method
overloading.
Overloading is having a method with the same name but different signatures overwriting on
the other
side is about changing the implementation of an inherited method.
Let's take a look at an example.
So throughout this course we learn about the Shape class so it's the base class where are
imaginary
PowerPoint application.
The Shape class can have properties like with height position and so on and it can also have
some methods
to keep things simple.
I've only added the draw method here now where we do have a class like circle or image
from the shape
.
The algorithm we use for drawing a circle or an image is different so that's where we need to
change
that implementation of the drama that we inherited from the parent Shape class.
Doing this in C Sharp is very simple and that's where we use the virtual and override
keywords so we
can change wer example to something like this.
So all we do here is we decorate the dramas in the base class with a virtual keyword and that
gives
us the ability to change that implementation in a derived class and to do that we use the
override keyword
in the derived class.
No that we don't necessarily have to overwrite or change that implementation.
But if we want we can do so by applying the overwrite to that drama or in the derived class.
If we don't override that method the default implementation defined in the base class will be
inherited
.
Now this technique is extremely powerful and that's one way to implement polymorphic
behavior in C-sharp
.
Now I want to keep theory in this lecture to a minimum and focus on practicality.
So let's start coding and see polymorphism and method overriding in action.
OK the example is going to show we in this lecture.
I believe it's an eye opener.
So let's take a look at this piece of code I have written which is an example of a poorly
written piece
of code.
I'll show we how to change this code and make it much better.
So let's take a look at the classes we have in this project.
We have a class called Shape which has a few properties like width length and position which
is simply
an X and Y and an enumeration called Shape type which determines the type of that shape.
Let's take a look at the shape type enumeration.
So shape type in an enumeration.
And currently we have support for circles and rectangles.
We also have a class called Canvas.
Here's our canvas class so this class simply has a method called draw shapes which receives a
list of
shapes.
Inside this method we iterate over the list of shapes and then we do a switch on the type of
the shape
.
So if the shape type is circle here we have an algorithm that draws a circle or if the shape is
rectangle
.
Here we are going to have the algorithm for drawing a rectangle.
Now this code has a problem and even though it's a classic example that I'm using for
teaching.
I've seen the exact same pattern in many real world applications so let's see what's the
problem with
this code.
The problem is that next time we decide to add support for a different type of shape let's say a
triangle
.
We have to go here to shape type enumeration.
Add a new member here triangle and then we have to go modify the can with class.
Here we are going to have another case statement like.
Case shape type that triangle.
And of course here we're going to have some algorithm for drawing a triangle.
The problem is every time we define a new shape type.
This method is going to be changed and as a result the class that contains this method has to
be recompiled
and redeploys which means any class in the application that is dependent on this class also
needs to
be recompiled and redeployed.
Same for the shape type every time we modify this enumeration and add a new member any
classes that
is referencing this again is going to be recompiled.
So there is a lot of tight coupling here and there is also an other problem.
Take a look at the canvas class.
Imagine if we're going to have support for 10 different types of shapes.
This method is going to get really really fat.
Well we may argue that we can refactor some of this logic here into separate methods but still
the
parent method here draw shapes is going to be fat and complex.
Now the reason we have this problem with this code is because the shape class itself has only
properties
it doesn't have any behavior it doesn't have any methods like the encapsulation principle of
object
oriented programming.
We want to encapsulate data and behavior or methods in the same unit.
That's a class application design or develop this way like the one we see here have data
somewhere
whereas behavior is somewhere else.
In this example data is here but behavior is inside is Kamis matter.
So we need to encapsulate them into one unit.
So let's see what's a better way to write an application like this.
So the first thing is I'm going to create a new class called circle.
Currently we don't have inheritance here.
We just have a shape class that has a type.
So let's create a circle
and be derived from shape
and another class Rectangle is also a shape.
Now I'm going to get rid of this enumeration here because I want the concept of type of shape
be determined
in a derived class so a circle is a type of shape rectangle is a type of shape.
We don't need the shape type enumeration anymore so let's remove this.
And obviously I remove it from the solution here as well.
Now back to our canvas class.
Obviously this code is broken because the enumeration doesn't exist anymore and that doesn't
matter
at all because as we explained here is the behavior around the concept of a circle.
So we need to encapsulate that behavior and the data related to that behavior in one unit.
So we go back to our circle class here first bonito either method here called draw.
So the drama that defines the concept of drawing a shape.
Now this method will be inherited by these derived classes but how we draw a circle is
different from
a rectangle.
The algorithm is different.
And that's where we use method overwriting.
So we declare this method as virtual.
So we get a chance to change its implementation in a derived class.
So here I go to the Circle class we simply type override.
And note that visual studio automatically lists all the methods that we can overwrite.
So here is the draw method.
And here are three methods that we have inherited from the base object class.
Equals get hash code and to string.
I will show we an example of overwriting one of these methods later.
So let's just get back to our draw method here.
Now by default visual studio automatically as this base draw method call here what does it
mean.
Base is a reference to the parent class.
So here we can write any code specific to the Circo class itself.
And then before or after if we need to we can pass the execution to the dramas that define in
the parent
class.
In this example we don't really need this because the drama that we have in the parent shape
class has
no implementation.
It's just an empty method.
So remove this and here I'll have the algorithm for drawing a circle.
Let's get back to our canvas class.
Now that here is the algorithm for drawing a circle which was not encapsulated with the data
about a
circle in one unit.
The behavior was different somewhere else in the application.
And that's a symptom of poorly designed application.
So I just cut this from here and put it back here.
We do a similar technique with the rectangle class.
So override tab and enter.
We don't need this line.
Now let's get back to the campus and grab this line which is we're drawing a rectangle
and paste it here.
Now let's go back to the camis again.
So we don't need the circle and rectangle anymore.
Elysée crafting our application does not have support for triangle.
Then I'll show we how we can add support for triangled without breaking existing code
without the need
to recompile and redeploy many classes.
So let's get rid of all this switch block here.
Now inside the foreach block what we do is we simply call the draw method of the shape and
here's where
the magic happens.
Let's take a look here.
So the parameter or this method is of type list of shapes so every element of this list is going
to
be a shape object or an object whose type derives from the shape class.
And that's what we learn earlier.
So at runtime what happens here is we iterate over this list of shapes what we may have a
circle in
the first element of this list or the second element might be a rectangle.
So when we call this draw method here even though we are talking about shapes at runtime
that shape
object might be a circle or a rectangle.
So when we call the drama it the draw in the circle will be called all the drawing the rectangle
will
be called and this is what we call polymorphism.
So pulling in Greek means many more means of form.
Polymorphism means many forms.
So we see we have the concept of shape and the concept of drawing a shape.
But that concept can have different forms depending on the objects we have and run time.
Let's get back to the campus class again.
Look at the implementation here is very simple.
OK now let's go to the program class.
Here in the main method first we create a list of shapes.
Then we create a canvas and we passed a list of shapes that draw shapes method on the
canvas.
Previously I used that type enumeration and that's why.
Because I deleted the type enumeration.
This code is now broken.
Basically what we need to do here is to store different types of shapes in this list.
So I want the first object to be a circle so
assign a new circle here.
And let's not worry about setting the properties.
And here let's put the rectangle
now to show we exactly what happens of runtime.
I put a breakpoint here real f 9.
Run the application into debug mode with f 5.
Now we can't step into this method with F 11.
OK now let's put a watch on the shapes object passed to this method.
So in the watch window type shapes.
So that's a list with two objects.
Let's expand this list.
Note that the first object is a circle and the second one is a rectangle again because it's a list
of
shapes an element in the list can be a shape object or an object was typed derives from the
shape Achillas
collapses.
Now we continue execution with 10.
One more one more one more one more.
Now we are inside the for each block.
Let us put a watch on the shape object.
So here is the current shape and as we see it's a circle.
Let's continue exaction with F 10.
No we step into this method with F 11.
Note that now we are inside the drama of a circle.
So let's continue execution with 10 or more one more one more.
Now this I torsion is over.
Let's continue execution.
Here is the second alteration.
And note that in the watch window now our shape object is referencing a rectangle.
So if we continue execution here.
Now we step into this drama.
It takes us to the drama of the rectangle.
Analysis of the debugger which shift an EF 5.
So back to our campus class again I want to emphasize this one more time.
So even though here we are dealing with a list of shapes and runtime the objects we have in
the list
can be a shape or any object was type derived from the shape.
Now because we declared the dramas are in the shape class as virtual That gives us the ability
to override
it in derived classes which means at runtime.
If this shape is a circle the draw method of the circle will be called.
Or if it's a rectangle the draw method of the rectangle will be called.
Now what's the benefit of this approach.
There are a number of benefits.
The first one is if we remember.
Previously we had various algorithms in this dropships method.
We had the algorithm for drawing a rectangle we had an algorithm for drawing a circle and
imagine as
we add support for more shapes.
This method is going to get fatter and fatter.
We fix this problem by using encapsulation such that we encapsulate the concept of drawing
a circle
as well as the attributes or properties about a circle in one unit.
So here if we want to have some extra properties about the circle we can define them here.
All these members in the circle class I highly related so pieces of the code that are related are
in
one unit as opposed to all over the place.
So this way the circle class doesn't get bulky because it only knows about the concept of
circle.
Similarly the canvas class doesn't get bulky either.
The implementation is very simple.
Now tomorrow if I decide to add support for a different type of shape let's say a triangle.
This method is not going to change.
Let's see what happens.
So we go back here to our shape file and this create a new class
called Triangle and derived from shape.
And now overwrite the drama.
And here we implement the algorithm for drawing a triangle so cancel that right line draw
correct.
Sorry triangle.
Now the interesting thing here is we simply added a new class called Triangle.
But this had absolutely no impact on the shape class because shape class knows nothing
about Triangle
.
It also had absolutely no effect on the rectangle rectangle is not changed it's not a factor.
Same for circle and same for Calvus are our campus class only knows about the shapes
whatever shape
they are at runtime.
Who knows who cares.
The canvas doesn't have to worry about it.
So this way with polymorphism we can create new shapes by simply creating new classes.
And that has absolutely zero impact in our existing classes.
And this is a sign of loosely coupled applications.
Well that's pretty much it for this lecture.
I hope we enjoyed it and thank we for watching.

So we go to abstract classes and memorise it with we.


I'm going to talk about the abstract modifier that can be applied on classes and their members
including
methods and properties and then I'll tell we about the rules that we need to know about
abstract classes
and members.
So what does the abstract modifier do.
The abstract modifier indicates that a class or a member is missing implementation.
It's easier to explain this with an example.
Here's the example we had earlier in the section.
So we have a Shape class with a draw method that is declared as virtual and we have a circle
class that
derives from the shape in the circle class.
We overwrite the drama.
And here we provide the implementation.
We're drawing a circle.
Now here we have a problem.
The problem is that it's hard to define an implementation for drawing of a shape.
How do we draw a shape.
It doesn't make sense.
We'd be talking about a circle.
We know how to draw a circle.
Or when we're talking about a rectangle we know how to draw a rectangle but it's impossible
to define
how to draw a shape because the concept of shape is too abstract.
In situations like this and better approach is to use the abstract modifier so we can declare the
draw
method as abstract to indicate that this method is missing implementation and we leave it to
the derived
classes to provide an implementation for this method.
So to use the strict modifier the code changes to something like this.
Note that here the draw method is declared as abstract.
And that's the reason it doesn't have implementation so it doesn't have a body.
It's just a declaration.
And here we terminate that declaration with a semicolon when we declare a method or a
property as abstract
the class that contains that needs to be declared as abstract as well.
So here the shape class is declared as abstract with this declaration.
We are telling that the shape class is missing implementation and that implementation needs
to be provided
by its derived classes in a derived class like circle and simply override the abstract methods in
the
base class.
So abstract methods are inherently virtual and can provide polymorphic behavior as we have
seen earlier
in the section.
OK now let's review a few rules that we need to know when working with abstract classes
and members
.
The first one is that an abstract member cannot include implementation.
So as we saw in the previous example the dramas didn't have a body.
It was purely a declaration.
The second rule is that if a member is declared as an abstract the containing class needs to be
declared
as abstract to
the third one.
Is that in a derived class we must implement all abstract members in the base abstract class.
So in this case our shape method had only one abstract method that was draw.
If it had three abstract methods we had to override all this three abstract methods and the last
one
is abstract classes cannot be instantiated.
So when we declare the shape class as an abstract we cannot create a new instance of shape.
So this line will compile.
Now we may wonder why do we use abstract.
What's the benefit we use Amtrak when we want to provide some common behavior while
forcing other
developers to follow wer design.
What do we mean by that.
Well in our shaping example are declaring the draw method as abstract.
We'll make sure that anytime a developer derives a class from the shape they will provide an
implementation
for the draw method.
If we did not declare this method as abstract and instead provided an empty virtual method
we would
run into the risk of a developer deriving a class from the shape without overriding the draw
method
.
In that case drawing that object would not make sense it's easier to demonstrate that in the
code.
So let's start coding.
OK let's create or shape class first.
I'm not going to use the abstract modifier yet because I want to show we the problem and
then explain
how the abstract modifier resolves that problem.
So here our ship can have a few properties.
Let's just give the width and height and a method for drawing the shape
.
So as I explained we cannot define an implementation for drawing a shape.
We have to leave this method as empty.
Now let's put this in a separate file
here back to our program.
Now let's create a circle class.
And here we override the draw method.
Nothing we so far.
So let's just put this in a separate file.
Imagine we're designing this as some kind of framework.
So in wer framework we're providing the concept of a shape and a circle in the future.
Other developers may extend on this topic.
They may define new kinds of shapes or it doesn't have to be other developers.
It could be werself.
So let's say sometime in the future we decide to add support for a rectangle.
So what happens is we go to the program create in wer class wer rectangle and derived from
shape
.
But accidentally we don't override the draw method.
Now let's see what happens.
So we go to the main method we create a circle.
We draw a circle and then we create a rectangle
and draw the rectangle as well.
Let's run the application.
So here's a problem.
We get a circle on the screen not another rectangle because we accidentally left out the
implementation
.
So here is where the abstract modifier can help.
So we can go back to our shape class and say we have some common behavior with some
common properties
about the concept of a shape that we implement here.
But there are behaviors here that we would like to leave to the derived classes to implement
the drama
theory it an example of that.
So instead of creating an empty drama set here we can't just declare it as abstract
and of course we need to get rid of the body and add a semicolon here.
Note the red underline here.
Put the mouse wer abstract method in non-abstract class because the dramaturgy is abstract.
The shape class needs to be declared as an abstract as well.
Now let's add another method here that doesn't have to be abstract.
Let's say every shape needs to have the ability to be copied into clipboard so we can have a
copy method
here.
We simply copy this shape to the clipboard and perhaps this implementation would be
common across all
derived classes.
We don't need to change any implementation in the circle or in the rectangle.
So here we have some common code.
Copy shape into clipboard.
We could have other methods here like select.
Perhaps when we select that shape in our PowerPoint application we would like to display a
highlight
around the shape.
Select the shape.
OK now that we declared this draw method as an abstract Let's take a look at the rectangle.
So here's our rectangle class and note the red underline it says.
Abstract the inherited member draw is not implemented.
So this way we create some kind of safe do some kind of guard.
Make sure that everyone including ourself follow the design.
So what we do here is we put the cursor here with resharper we press alt and enter and the
first item
is implement members and resharpen automatically creates overwrite methods for any
abstract methods
we arrived in the base class.
So let's implement this method here.
Draw a rectangle.
Now we run the application.
Know that we get both.
Draw a circle and draw a rectangle.
So here is the benefit of abstract modifier.
It's not something that we use every day in wer programming career but it's a tool that we can
use
when we're facing situations like this when we want to force wer design to be followed
everywhere
in the code base.
Now before we finished this lecture I want to show we a couple more things.
So first let's put this rectangle class in a separate fine to clean up our code.
Back to the program.
Look here.
I cannot do something like this.
We cannot instantiate shape because shape is declared as abstract and that's the reason we get
this
read on the line here.
The tooltip says cannot create an instance of the abstract class shape.
Here's yet another reason to use abstract because what does a shape represent.
It's too abstract we cannot imagine a shape in our PowerPoint application.
There are PowerPoint application we have concepts such a circle a rectangle or image or
table shape
doesn't make sense.
We can just use shape as the base class that provides some common behavior but it shouldn't
really be
instantiated.
So let's come in this out OK.
In the dog framework we have a class called stream which is the base of all types of streams.
Earlier in this course I show we a fine stream and memory stream.
In case we missed that lecture of Esquith we reveal that here.
So we go to view object browser
and here we can type file stream.
So file stream is a class that is declared in-system the I O namespace.
I look at the declaration of this class here.
So file stream derives from system dot IO dot string. Stream is an abstract class which means
we cannot
instantiate it.
Let's take a look at this class look.
Stream is selected here.
Here we see the members declared it is class and here is the declaration of the class itself.
It's a public abstract class.
Again here is another example where some concepts needs to be declared as abstract.
For example what does a stream represent.
A stream is too abstract but file stream is very specific.
It provides ways to read from or write to a file or memory stream is a kind of object that
allows us
to read data from memory or write data to memory or the stream itself is just too abstract.
So that's the reason the developers of Dathan framework have declared it as abstract.
And by doing so they have provided some common behavior that we can see in some of the
methods here
.
But they left the implementation of some of the members to the derived classes like 5st more
memory
string.
Ok that's pretty much it for this lecture.
I hope we enjoy it.
And thank we for watching

OK earlier we learn about abstract classes.


Classes are the opposite of abstract classes.
So a cild modifier prevents the right version of classes or overwriting of methods similar to
the abstract
modifier.
The still wanting for it can be applied to a class where a class member if applied to a class.
It prevents direct vision of classes from that class and if applied to a method it prevents
overwriting
of that method.
Let's take a look at an example.
So here's a circle class that we saw in the last lecture.
It derives from the Shape class and overrides to draw method.
We can apply the sealed modifier to the Circle class by doing so we can not create a class that
derives
from circle.
Or we can apply the sealed modifier to the dramas here.
Note that ceiled modifier can only be applied to methods that are overriding a virtual method
in the
base class.
So if we're not overriding a method that is declared as virtual in wer base class there is no
need
to apply sealed.
Now we may wonder why do we need sealed.
Well the MSDE documentation states that ceiled classes are slightly faster because of some
runtime optimizations
.
But personally I think that slight optimization is not going to make a difference in the
performance
of wer application.
In fact seal is one of those features that is hardly ever used personally over the past 12 years
of
working with C-Sharp and the Dutton's framework.
I've never felt the need to market class remember as sealed.
In fact I think it's an anti-pattern because if we're going to play ceiled to some of her classes
for
a slight optimisation we are going to mess with wer inheritance hierarchy.
So that can affect the design and the development.
So as a guideline I suggest to we not to use field unless we have a very strict reason for doing
so
.
If we have made certain assumptions in the class and we don't want other classes to and heard
from
that class that's ok go ahead and use yield.
But another reason I added sealed in this course is because there are classes in inductive
framework
that are defined as ceiled which means we cannot inherit from them.
An example of that is the string class we cannot inherit from the string class.
So if we want to extend it we need to use extension methods extension methods is an
advanced topic
and have covered it.
In my C-Sharp advanced course that we can find Anyuta me.
That's pretty much all we need to know about ceiled classes and members.
I hope we enjoyed this lecture and thank we for watching

OK we got to interface's which is one of my absolute favorite topics in this section.


I'm going to talk about what is an interface how to declare and implement interfaces and then
I'll explain
how interfaces improve the testability and extensibility of wer application.
So what is an interface.
An interface is a language construct that is similar to class in terms of syntax but it's
fundamentally
different.
Let's take a look at the scene text first.
So here is how we can declare an interface instead of using the class keyword we use the
interface keyword
and note that in dot net all interfaces start with the letter.
All right.
So wherever we see a type that starts with I that represents an interface it's a convention but
unlike
classes interfaces do not have implementation.
So we see here we have a method called calculate that is simply a declaration.
It doesn't have a body.
It doesn't have curly braces.
Also note that interface members do not have access modifiers.
So here we don't have public private protected whatever.
Now we may wonder why do we need to construct like that.
Well in simple terms interfaces are used to build loosely coupled applications.
That is an application.
Those components are not tightly related to each other which means making a change in one
of these components
is easier and it has less or zero impact on other components.
Let me use an analogy think of the concept of a restaurant and a chef.
We can say a restaurant needs a chef with certain capabilities.
By that definition we can fill that role with anyone anyone who has those capabilities can fill
the
role of the chef for that restaurant.
So the dependency between the restaurant and the chef is loose.
If something happens to that chef like he gets sick or he decides to move on to a different job
we can
fill that role with someone else.
Now in contrary if we said a restaurant needs John as a chef that means we are very
dependent on John
.
If something happens to John if he decides to not to come to work then the restaurant is in
trouble
.
So this is a definition of a tightly coupled dependency.
The restaurant is tightly coupled tightly of relator tightly dependent on John.
Now I use this analogy to explain that when building software we want or classes or our
components to
be loosely related or dependent on each other.
So if we decide to make a change in one of these classes it has minimal or zero impact in
other classes
.
Take a look at this picture.
Here we have two classes.
Order processor and tax calculator and this UML diagram we'll see a dependency as
demonstrated here
between an order processor and tax calculator.
In C-sharp terms that means order processor has a field or a property that is of type tax
calculator
.
Now this is an example of type coupling between ordered processor and tax calculator.
If we make a change to these tax calculator here it may affect the order processor and
subsequently
any of the classes that depend on order processor.
Now we use interfaces to reduce this coupling.
How well we can change this picture to something like this.
So in sort of order processor being dependent on tax calculator it's going to be dependent on
an interface
that is I tax calculator and interface as we saw earlier it is simply a declaration.
It's not a concrete class.
It doesn't have code.
It's methods do not have a body.
So as long as we keep that interface the way to use as in like we are not going to remove any
obvious
methods or changes parameters.
It's not going to have any impact on the order processor.
Now if we decide to change the algorithm for calculation of tax we can create different
classes that
implement this interface here.
And that would have absolutely no impact on order processor if that concept is new to we.
Don't worry about it.
I'm going to show we exactly how it works in code.
Interfaces are extremely powerful and once we really understand them we're going to fall in
love with
them.
So in the rest of this section I'm going to explain how interfaces help improving the testability
and
extensibility of wer application.
So thank we for watching and I'll see we in the next lecture

OK so in this lecture I'm going to talk about interfaces and testability.


I'm going to show we how interfaces improve the testability of wer application.
This lecture is heavily focused on coding and we're not going to have any slides.
So let's jump into Visual Studio and see how interfaces help improve the testability of
applications
.
OK in this example we are going to see a very basic pathetical order processor in a real world
application
and this is going to be far more complex.
But I have removed all of that complexity here because we just want to focus on testability.
So let's see what's happening here.
We have an order processor here.
We'll take a look at that in a few seconds.
We also have an order object.
And finally we call the process method of the order processor.
I seem to order object.
Let's take a look at the implementation of this method to get there simply press shift control
alt and
B.
There we go.
So here's our order processor class.
It has a field that is read only in private type shipping calculator.
So we use this calculator to calculate the shipping cost as we will see shortly in the
constructor
here.
We instantiate this object.
And here's our order processing method.
So in the process method we get the Order object first we see an example of defensive
programming.
So first I'm validating if the order is already shipped.
If it's shipped I don't want to ship it again.
So a bit of defensive programming is good to have in wer methods to make sure that we don't
take the
state of system to something that is unexpected.
But on the contrary if we're going to do too much defensive programming wer code is going
to be bloated
with too much validation.
So at this point I think it's just enough to see if order is shipped and we throw an exception an
exception
of type invalid operation exception which states whose order is already processed.
Now if the order is not shipped before we simply create an object of type shipment and assign
it to
the shipment property the shipment class has two properties cost and shipping date to
calculate the
costs.
We use our shipping calculator.
So we passed the order and that shipping calculator knows how much the shipping cost
should be for an
order for shipping date.
I have hardcoded a rule here that states shipping will be done the day after the order is
submitted
.
Again this is a hypothetical scenario and it's most likely not the case in real world
applications.
Knownas take a look at the calculate shipping method here.
So simply put wer cursor here press shift control alt and be OK in this method.
We have a simple rule.
So if the total price of the order is less than 30 dollars the shipping costs is going to be 10
percent
of the total price of the order.
Otherwise if the order is 30 dollars or more we're going to give a free shipping to our
customers.
So pretty basic.
Now let's get back to our order processor.
Ok let's say we want to write a unit test or this process method here.
If we have never done unit testing before it that's perfectly fine.
I'm going to introduce we to the concept of unit testing briefly.
Know that unit testing is a comprehensive topic and is way beyond the scope of this course.
And I definitely plan to create a comprehensive course explaining the best practices of
automated testing
for C-Sharp applications.
But at the time of recording this it's not ready in case we want to be notified about that course
when
it's ready.
Follow me on Twitter or Facebook or my WeTube channel.
The details are in the introduction section of this course.
OK let's move on and see what is unit testing all about unit testing is part of automated
testing practice
which means we write code to test our code.
So instead of we manually test our suffer every time using clique's and typing we write some
automated
tests to achieve that.
Now let's see how this happens in practice.
So in solution explorer here I'm going to right click and go to add new project in the left
section
under visual C-Sharp we'll see test.
So we select unit test project.
I'm going to name it after my project got tests.
So in this case my project is called testability which is the name of this lecture.
I'm going to name my unit testing project testability tests or better unit tests and wer project
whatever
is the name of wer project.
Just put that here instead of testability.
Let's press enter.
OK here we have a unit testing project by default visual studio create a test class for we here
which
is called Unit Test 1.
Note that each test class as an attribute called Test class and it can have a bunch of methods
like
the one we see here which are decorated with test method attributes in C-sharp attributes
represent
meta data about wer classes and their members.
They don't have any logic there are just markers.
Then another application or another assembly can read this method data and do something
about it.
For example later we're going to see that we're going to use Microsoft test runner and that test
runner
is going to look at all classes that have a test class attribute and then it's going to run the
method
and have a test method attribute like here.
OK before we write our test let's take a look at our order processor and see what kind of test
cases
we need to write.
So back here.
OK.
Take a look at this process method here.
Here we have two execution paths.
One is if the order is shipped are going to throw an exception.
The other one is if order is not shipped we are going to change the state of the order by
setting its
shipment property to a new shipment object based on some values here.
Now there is a problem here.
The problem is that when we need to test the class we need to isolate it which means we need
to assume
that every other class in the application is doing its job properly.
So we can write tests around this class and that's why we call this practice unit testing.
We are focusing on a single unit of functionality without dependency on any other parts.
Now in this sort of processor class we have tight coupling to shipping calculator.
Look here we have a shipping calculator which is instantiated in the constructor of order
processor
.
So because of this tight coupling we cannot isolate this class.
So when we write tests or this piece of code here this depends if the shipping calculator is
going
to be a problem.
How do we solve that using an interface.
So let's go to our shipping calculator class
this shipping calculator has one method called calculate shipping.
We need to create an interface that has this functionality and then have this shipping
calculator implement
that.
What does it mean.
Remember the analogy I use for the chef I said the restaurant needs a chef who has certain
capabilities
whether it is John or Mary or Steve.
It doesn't really matter as long as that person can fulfill some needs based on some standards.
It's exactly the same scenario here by using an interface where de-funded role that drool of
calculating
shipping know which class is going to fulfill that role.
It's a separate issue in this case.
This class is going to be filling that role.
It's like John being a chef.
Now let's create an interface year so similar to a class public interface.
We give it a name I shipping calculator.
Note that the name of the interface is prefixed with capital I and that's a convention in the
framework
.
Now here we need a method called float calculate shipping which takes an order object.
Note that this method does not have a body like this.
If we do that we see this read on the line here highlighting an error.
So let's do that.
Also there is no access modifier here so we cannot say public private whatever.
So it's not going to work.
This interface simply defines the capability that a class should provide.
Now we need to have this shipping calculator class implement an ice shipping calculator
interface how
we go here and type colon shipping calculator.
It looks a little bit similar to inheritance right.
But this is not inheritance because with inheritance we write code once and then reuse it.
We don't have to type it again but in this case we see we have this method declaration here.
But we had to manually type all this code here.
So this is not inheritance.
We read this as a shipping calculator implements i shipping calculator.
OK.
Now that we have this interface Let's go back to our order processor.
Instead of being dependent on this concrete class which is like John as a chef.
We want to be dependent on an interface like the role of the chef in a restaurant.
So what I going to do is simply put this on here.
I know we have an interface and instead of creating a new object of shipping calculator here
we need
to initialize this field using the constructor.
Why.
Because here we're still dependent on that concrete shipping calculator class.
So what we need to do is we go here pass a parameter of a shipping calculator type shipping
calculator
an initialized our shipping calculator filled using this argument
look.
Now there is no reference to the shipping calculator concrete class we're just referencing an
interface
and this is an example of loose coupling.
So if we go back to the shipping calculator class and we change its coat let's say we add a few
new
methods or change this logic here.
It's not going to have any impact on our order processor class or the processor doesn't know
about shipping
calculator it just knows there is a class that can fulfill that need.
Now if we build our application at this stage it's going to fail.
Let's take a look control shift P to build build failed let's double click this error.
Look in the main method here.
When instantiating an order processor object we need to pass the shipping calculator look it
needs an
instance of shipping calculator.
So here we need to specify that concrete class which is shipping calculator.
Now here we might be thinking isn't that dependency to shipping calculator.
Yes it is.
What is the main method here which is outside that class.
The main method here is like the matchmaker.
It knows different concrete types and ties them together or none of these concrete types like
the order
processor knows about the existence of other concrete types.
So in this case it's perfectly fine to instantiate this shipping calculator object here.
Let's build again.
OK the project is working.
Now let's get back to our order processor and review our test cases.
There we go.
So the first Test we need to write is if order is shipped.
This method is going to throw an exception.
Let's see how we write a test for that.
So I'm going to open that unit test one file here which is inserted into the test project by
default
.
I'm going to rename it.
We can press control r and then or again or two because we're writing tests for order
processor.
The name of this class should be Order processor tests.
Now the name of this method should be based on a convention like this.
We have the method name on the line the condition that we are testing.
Underline expectation.
So here's the pattern.
Let's see how it works.
So in this case the name of method we're testing is process.
The condition is order is already shipped and the expectation is throws an exception.
So not that the method name is very descriptive.
It can act as a documentation.
OK now let's see how they can write a test for this class.
So the classroom testing is order processor Let's create an object of that type of wire order
processor
because new order process order processor.
Now because I'm using recharter I can easily press Hultin enter here and the first item is
referenced
testability and used to stability that order processor.
The reason for that is because we are in a separate project in our uniters project.
We need to reference that project so we can use the classes defined there.
So I'm just going to go ahead with the Sharper's refactoring.
If we don't have resharpen we need to go here.
Right-Click references go to ide reference and then under solution under projects take a
testability
.
OK so here we have the order process or object but we have to specify its dependency wishes
i.e. shipping
calculator.
Now what do we need to pass here.
We need to pass a fake object that is always working.
We are not going to pass that original shipping calculator because we're trying to isolate that
order
processor right.
So let me create a fake shipping calculator.
So public class fake shipping calculator is class should implement shipping calculator
interface.
No just read on the line here that is here because we have not implemented this interface
which means
we have not defined the methods that are declared in that interface.
So for that to happen we need to press alternate enter and enter the shortcut always works
whether
we have resharpen or not.
Now we see we have this method called calculate shipping based on the declaration in that
interface
.
And note that this method is automatically declared as public.
If I change it to private
compiler is going to complain because method is declared in an interface should be public.
So basically as we see an interface defines the public interface or the public functionality or
the
public service that a class provides.
All right.
In this method I'm just going to hard code a simple number because we're not going to have a
logic.
We are assuming this fake class is doing its job properly.
And our focus is on testing the order processor.
We were trying to isolate we.
Right.
So let's pass an instance of this fake shipping calculator here.
I know I want to create an order that is already shipped.
So let's create an order.
How do we know if the order is already shipped.
Let's go to the Order class.
Look here I defined a property called is shipped that checks if the shipment object is not no.
So if the shipment object is not now this property is going to return true.
So back to our tests what I'm going to do is simply use the object initialization syntax year.
And at the same time I'm initializing the order.
I also initialize is shipment property to send it to an empty object.
This way is ship property is going to return true.
Now it is called the process method.
So order processor that process and pass the order object.
So here what we need to assert is that an exception is thrown with the default testing
framework that
comes with Visual Studio.
We can achieve that using an attribute here that's called expect that exception here we need to
specify
the type of exception so type of invalid operation exception.
Now that here we are using Microsoft testing framework.
If we're using other testing frameworks like an unit or x unit or whatever the implementation
could
be slightly different but the concept is exactly the same.
We have to isolate the class using an interface we need to arrange some preconditions we
need to act
on a method.
And then finally we need to do assertions.
OK now let's run this test and see what happens if we have sharper.
The shortcut is controlled and are without sharper we press control are and then a if we forget
the
shortcuts simply go to test menu.
This is Visual Studio testing framework on the run.
We see we can run all test using that shortcut.
We did reach our prayer we go to unit tests and control T and R as specified here.
So let's run this
.
That we got a green tick here.
Now let me show we something if we go back because this if we go back to order processor
and comment
out these two lines here and then go back to the test class and try to run this test again.
Note that this time the test failed and we got these red icon here.
So the description here explains that this method did not throw an exception which was
expected from
the process method.
So this close these like to our Order order processor class.
Let's bring this back in.
OK.
Now let's write the second test case.
So if the order is not shipped we want to make sure that the shipment property is initialized
properly
.
So we go back to our test class
following the same pattern here.
We're going to write another test mitha.
Public void the method we're testing is prosess.
The condition is order is not shipped.
What should happen should set the shipment property of the order.
We decorate this method with test method attribute.
Now all we need to create an order process or object so we can simply go here and copy paste
this code
here is done.
I'm going to create a new order object but I'm not going to initialize the shipment property so
is shipped
is going to be false.
I know if we call this order processor that process method has in the Order object
we need to assert that the order the shipment is initialized properly to do that we use the
search class
that comes as part of the test framework.
This class provides a bunch of useful methods for various kinds of assertions.
First we want to make sure that is shipped is set to true so is true.
And we pass order.
God is shaped as an argument.
We did a couple of more assertions here let me scroll down so we can see this better.
OK let's get back to our order processor.
Look apart from this shipment property being initialized.
We also need to make sure that the cost is set properly and shipping date is set to tomorrow.
In this case because we are isolated our order processor and passed a fake shipping calculator
here
.
If we remember that mezza always returns 1.
So we need to assert that the cost is set to 1 and for shipping date we can assert that it's set to
tomorrow.
So let's get back to the test method.
OK I'm going to write another assertion here.
So assert dot this time I'm going to use the are equal method.
The first argument to this method is the value that we expect.
So the cost should be one.
The second argument to this method should be the actual value which is going to be an order
that shipment
cost and write a similar assertion around the date to make sure that the date is calculated
properly
assert that are equal the date should be tomorrow so date time the hot day on day 1 and the
actual value
which is the second argument to the our equal method is order Dutch shipment that shipping
date.
Let's run this test.
So that has passed.
OK.
Before we finish let's recap.
So back to our order processor.
Previously this class had a field of type shipping calculator.
And because of that it was tightly coupled.
Implementation.
We reduced the coupling by introducing an interface I shipping calculator with an interface.
This class is no longer dependent on a concrete class which means we can isolate it during
unit testing
.
So the takeaway from this lecture is when we're trained to unit test wer classes if that class
has
other dependencies in terms of concrete classes we can use an interface to reduce that
coupling before
we finish this lecture.
Let me show we a quick way to extract the interface from an existing class.
So let's get back to our shipping calculator.
Imagine we didn't have this interface before.
So I'm going to get rid of it.
So here is the original shipping calculator class.
If we have read sharper We can press control shift and or to activate refactoring options.
But unfortunately that shortcut is not working for me here because I'm using a Mac keyboard.
So the alternative way IIS right click the type here go to refactor.
This is part of visual studio refactoring tools and we will always have this whether we have
resharpen
or not.
Then go to extract and extract the interface
and it's not unboxed we see the name of the interface automatically populated for we.
I shipping calculator.
And here we can take all the members of this class we would like to extract in the interface.
In this case we have only one method and that's why we see only one item here.
So let's click next.
There we go.
We got an interface here and that is automatically implemented by shipping calculator class.
So this way we don't have to manually go and type it all I just did it before because I wanted
to show
we how to create an interface from scratch in the next lecture.
We'll see another use case of interfaces and bodies or increasing extensibility of an
application.
I hope we enjoyed this lecture and thank we for watching.

In the last lecture we saw how we used interfaces to improve the testability of our
application.
In this lecture we're going to see how interfaces health with extensibility are application.
So similar to The Last Lecture.
We're not going to have any slides here.
So let's jump into Visual Studio and start coding.
OK let's if we like to create a tool for migrating a database we can start by creating a class
called
DB migrator
class can have a singular method called migrate which can be void.
And here we are going to have details of migrating the database now to keep things simple.
I'm not going to implement that here but what I want to show we is how we can create
extensibility
points here by using interfaces.
For now let's just assume that we would like to log some messages on the console as the
database is
being migrated for example we may want to display the time the migration started.
We may display the time migration finished if there were any problems along the way.
We can display them on the console.
So one way to implement something like that is to go here and say all right line
migration started at
and here we can have the current date time
potentially we can have another console in dot write line here to indicate where in-migration
finished
.
Now the problem with this kind of implementation is if tomorrow we decide to use a file or a
database
instead of the console we have to come back to this method and change it.
Which means this class has to be recompiled and redeployed.
Let me tell we something interesting here.
In an ideal world we would like to design or suffer such that we can change its behavior
without changing
its code.
We might wonder how is that possible.
Well it is possible by using extensibility which means instead of changing the code in the
existing
classes simply add in new classes that change the behavior of the system.
With this way of thinking every time we want to change the behavior of our solver we create
new classes
.
And as we learn from the last lecture we can write unit tests or any kind of automated test
only for
those new classes.
The impact should be minimal to zero on the existing classes because we are not changing the
existing
code.
Now as much as this idea sounds beautiful sometimes it's a little bit costly to implement.
So in practical terms we can not design software such that every change can be implemented
using an
extensibility mechanism.
Well it is possible but sometimes the cost of that is way too much and it's really not worth it.
But in this case in our DB my greater.
It is possible that someday in the future we may decide to log messages in a file or in a
database as
opposed to a console.
So how can we design this DD migrate such that it's extensible.
Well that's by using an interface.
Let's see how we can make this happen.
So instead of using the console directly here we should use an interface like logger.
Let's create an interface for that first
so public interface.
I logger.
Not that I'm prefixing that with capital I know lugger may provide methods like log error
which gets
a message or another method like log info is for simply logging information messages which
are not for
reporting problems in the code.
It's purely for troubleshooting.
Let's put this interface in a seperate file to clean up our code.
So back here alternate enter enter.
OK now back to the program and I'm going to do the same thing with DB migrator I'm going
to put it in
a separate file so alternate enter enter.
Now we want to change DB migrator to get and I logger interface.
So as we learn in the last lecture we need to create a constructor here and in the constructor
we inject
that interface.
So I lugger the colored logger and with resharpen we can press alternate enter here when the
cursor
is on the logger here and enter again and resharpen automatically create a private read only
field of
type.
I lugger So the technique we are using here is called dependency injection which means in
the constructor
we are specifying the dependencies where it is DB migrator class and later in the main
method as we
will see shortly.
We're going to specify a concrete class that implements that interface.
So this whole thing is called dependency injection.
Now in the migrate method instead of directly talking to the console we're going to talk to a
longer
.
So say logger that log info and I'm going to cut this message here.
And paste it here
except that I need to change it come on to plus because I have to concatenate them to form a
string
.
We're asking the console dot write line.
We were passing multiple arguments.
Let's remove that.
And I'm going to repeat the same thing here.
This time I change started to finished again to refresh wer mind remember the analogy I use
for the
restaurant.
They said the restaurant needs a chef.
Now whether that shift is Jonge or Steve or Mary it doesn't matter as long as that chef has
some capabilities
to a given standard.
It's the exact same scenario here so DPMI greater doesn't care who is the actual logger and
instance
of any class that implements this interface can be passed in the constructor here.
So there is no coupling between DB migrator here and that concrete class.
Now let's create a concrete class that implements that interface.
So the public class let's call it console logger because we use console for logging I lugger
not the red underline that's because we have not implemented the interface yet.
So we press haltered enter and enter.
Now here I'm using resharpen.
So it opens up the dialog box which allows me to choose which methods I would like to
implement.
And by default both of them are checked.
If we don't have resharper I think visual studio automatically implements all methods in the
interface
.
So let's just go with the defaults.
So for long an error I'm just going to use console dot write line and pass that message here
and to
make it a little bit more user friendly.
We can perhaps change the color of the font so say Konsole foreground color equals Konsole
color dot
red to indicate an error.
We can't repeat the same thing in the log in full method and it's sort of using red.
We can use say green.
Now let's put this class in a separate file.
OK let's take one final look at DB migrator.
So look it knows absolutely nothing about the console.
And it's just talking to an interface.
Now let's go to the program in the program.
We're going to create an instance of DB migrator.
So our DB migrator equals new DB migrator in the constructor.
I need to specify a concrete implementation of that.
I love our interface.
In this case we pass a console logger.
And finally we call them migrate method of the DPMI greater let's run the application.
There we go.
We got two messages on the console migrate -iong.
Sorry for the spelling it's migrating started at.
Here is the date time and we had a problem here with the formatting of string.
It doesn't really matter.
And we see the second message migrating finished at the time.
Now let's say the hypothetical scenario is going to happen.
So we decide it's full of luggin messages on the console.
We decide to log them in a file.
Let's see how we can achieve that.
So all we have to do is create a new class Pawlick class lugger.
It implements the I logger interface and repeat the exact same steps here.
So all 10 enter and enter again and again we got this method here.
So let's create a constructor that takes the name of the file.
So the tour area passes better and we press alt and enter and again so we got the private field
here
and in the log error method we need to create a stream writer or writing data to a file.
So News Stream writer know that this class is defined in System done.
Io namespace as we see here.
And because I'm using sharper resharpen automatically either the using namespace for me
here so it makes
wer life much easier.
Mike here now in the constructor or stream writer I need to specify the path.
So I use that private field and the second argument specifies whether we like to append for
that file
of course.
Yes.
Then we can call dot write line method and pass that message here.
There is just one problem here.
The problem is that this stream writer uses a file resource. A file resource is not managed by
CLR
or a Common Language Runtime which means we need to dispose that resource once we
finish using that
.
The easiest way to do that is to wrap this whole block here in a using statement.
So let's see what happens.
I moved this large stream writer inside using.
And then in the using block I move this stream right writer dot write line here.
Basically what happens behind the scene is there is an exception handling mechanism inside
this using
that we're not going to see it's implemented by the compiler.
So if something goes wrong an exception is strong or something the compiler will make sure
to close
the file handle by calling the Dispose method on the stream writer.
Let me share a method here so the stream writer do suppose this method is used or fring
external resources
that are not managed by C-L or when we use the using statement here the using block the
compiler automatically
includes a call to the Dispose method so we don't have to manually do that.
OK one last thing here.
Perhaps it's better idea to add a prefix string here to specify that this is an error because when
working
with a file we don't have colorists like as we did with Konsole so we can't say error plus
message could
potentially include the date time here as well but it doesn't really matter for the purpose of
this
lecture.
Now interestingly we need the exact same code for the log info method here but look we are
duplicating
code and there is a principle called dry or don't repeat werself.
So we can refactor this and make it a little bit better what we can do is we can create a private
method
call it log it gets a message and perhaps get another string like message type.
Let me scroll down so we can see just a little bit better.
And then I'm going to move all this code inside this method instead of using this hard coded
error prefix
here.
I'm going to use message type plus colon and a space and then I'm going to reuse this method
in both
log error and log in for methods.
So there's no code duplication anymore.
So I'm just going to call log past a message and the message type is going to be error.
I would do the exact same thing here with log info.
Now even a better way to do this is to use any anti-immigration.
So we should be familiar with enumerations.
But again I leave that to we as an exercise because I don't want to get too distracted with that
coding
practices in this lecture because we just want to see how we can use interfaces to create
extensibility
points in our application.
So I think for now I should do the job.
Let's put this class in a separate file.
So I put the cursor here Hultin enter and enter.
Good.
Let's review what we have done so far.
So back to our program.
See created a DB migrator and passed a console logger instance his constructor.
And finally here we called the migrate method.
Let's take a look at DB migrator so DB migrator talks to an interface.
It doesn't know what concrete class is going to implement this interface.
It doesn't really care.
Now at this point when we run the application messages are logged on the console.
We can't change the behavior of the application.
We're simply going to the main method and swapping that implementation with a different
implementation
.
So instead of Consta logger I'm going to use file longer specifying path.
So I'm going to use C. Kallen backset backslash.
A logged RTX XTi.
Actually this may throw an exception of my machine because I'm running this in a virtual
machine and
I don't think there is access to the root of C drive so I'm going to change the path to projects
back slash
back slash log dot txt.
Let's run this well that no messages are logged in the console anymore.
Let me go to the file system
.
So C-Drive projects Loek.
We have a log file here.
So in four messages are logged in this file.
We'll see there are four of them because I ran the application twice in the middle of
recording.
So don't worry about that.
There is no bug.
The first one says migration startup migration finished.
And then here we run that application again.
So we got two more messages.
So the interesting thing here is we changed the behavior of our application by simply creating
a new
class as we saw here by logger and simply passing that to this constructor here.
I did not change one line of code in DB2 my greater and this is what we call changing the
behavior by
extending application instead of changing the code in object oriented programming.
This is referred to as open closed principle or OCP which states suffer entities should be open
for
extension but closed for modification.
And in practical terms that means here this class should be closed for modification.
We didn't change anything here but this is open for extension using this extension point.
Now don't think that we always need to use an interface in scenarios like from console to file
system
or from file system to database.
Not necessarily.
That was just a simple example in wer application we might have an application that is
working on
a map like a GPS obligation like Google map and we need to calculate the shortest distance
between
two points.
We can use an interface like Route calculator that finds the shortest path between these two
points
.
Later in the future we may come up with a better algorithm maybe an algorithm that is faster
maybe
an algorithm that knows the traffic conditions or whether Street is one way or two ways.
We can't simply create a new implementation of that interface and inject that to wer class
without
changing the existing code.
Or let's say as another example in wer application we have some kind of encryption Maybe
we have
a class that needs to use an encryption service.
So in that case we can create an interface call or encryptor and create a class that implements
that
interface with a very basic encryption algorithm.
Later in the future we may come up with a better algorithm a better encryption algorithm and
we can
simply change the behavior of wer application by creating a new class that implements that
interface
.
So we've got the point.
Well that's pretty much it for this lecture.
I hope we enjoy it.
And thank we for watching

One of the common misconceptions about interfaces is that they're used to implement
multiple inheritance
in C-sharp and I have seen books videos and blog posts that make such a claim but
unfortunately that
claim is fundamentally wrong.
Interface's got nothing to do with inheritance.
Let's go to Visual Studio and see what they mean by looking at a piece of code.
OK in this project I'm demonstrating the concept of a UI framework so we have a class like
we I control
with a bunch of properties like ID size and top left.
Assuming that each we control like a text box or dropdown list can share these attributes.
It also provides a couple of methods like draw and focus.
It's a very very basic implementation.
Now let's create a class called Text Box public class text box and we can derive it from we I
control
.
So in some languages like C++ a class can have multiple base classes and this is what I refer
to as
multiple inheritance.
So we can have we eye control here and less Or sake of discussion say we can also we heard
from size
.
It doesn't make sense conceptually but just for the example look we immediately get a read
on the line
here because in our class cannot have multiple basic classes.
But what we can do here is to have this text box implement multiple interfaces so we can say
it implements
I Dragonball or I drop them all I know we have to implement these interfaces so often enter
later.
Now I mention that interfaces got nothing to do with inheritance.
Let me clarify that when we use inheritance for example when we do right from we I control
basically
we write all the code once here and then we don't have to type the game that text box
automatically
inherits all that code.
But what about interfaces.
Let's take a look at Idraggable.
That interface doesn't have any code.
It just includes a method declaration.
Same for I drop the ball.
There is no code.
So when we go and implement that interface in a class like a text box we have to type that
method declaration
again and then actually implement it.
So there is no code to inherit.
There is no reusability.
And that's the reason that I explain interfaces got nothing to do with inheritance.
On the surface from a technical point of view yes they look like they are based classes of the
text
box but this is just syntax.
It's fundamentally wrong to say a class inherits from an interface a class implements an
interface because
an interface as we see here is simply a contract.
It's saying that any class that implements this interface should have a method that is public
void and
called drop.
And that's what we type here.
So that's the truth about interfaces and inheritance.
Unfortunately when I started learning about C-Sharp and I came across this topic the book I
read told
me that interfaces are used to implement multiple inheritance and that statement as I
explained was
fundamentally wrong and it took me years to really get it for years.
I was confused and frustrated thinking how can we reuse code by inheriting from these
interfaces.
And the truth is that is not possible there is no code Driggers.
All we are doing is confirming to a contract we're making sure that the public interface of our
class
has the methods or members it has declared in the interface.
So I just wanted to clarify this to we in case we come across some books blog posts or videos
that
claim that interfaces are used for implementing multiple inheritance.
Anyone who says that definitely does not have a deep understanding of interfaces.
Interfaces are used for building loosely coupled extensible and testable applications not for
code reusability
.
What interfaces do provide polymorphic behavior and that's what I'm going explain to we in
the next
lecture.
I hope we enjoyed this lecture and thank we for watching

In the last lecture I explain to we that interface's got nothing to do with inheritance.
But interestingly they do provide polymorphic behavior as we learn in the section about
polymorphism
.
So in this field I'm going to show we how we can use interfaces to achieve polymorphism.
Let's get started.
OK in this project I have got a class called video encoder that is responsible for encoding of
video
.
It has a simple method called encode which gets a video object.
Let's take a look at the video encoder class.
Here is a code method for simplicity.
We don't have to worry about the video encoding logic but what is interesting here is that
once the
video is encoded we use the mail service to send an e-mail to the person who uploaded the
video to our
website.
Let's take a look at the mail service.
So again here to keep things simple we're not worrying about how to send an e-mail.
We just log in a message to the console.
Let's run the application.
So we are simulating that a video was encoded and we sent a notification e-mail to the person
who owned
the video.
Now let's get back to video encoder.
There are a couple of problems with this class.
The first one is this type dependency to mail service which is going to affect the stability of
this
class.
So earlier in the lecture about stability learned that if we want to unit test the class we have to
isolate it.
So instead of using a concrete mail service here it would be better to send an interface in the
constructor
and initialize an email service field here.
But there's just one problem.
There is another problem.
The problem is if tomorrow we decide to have another way to notify the person who owned
the video let's
say send them a text instead of e-mail or maybe both.
Then we have to come back to this method and change it.
Which means every time we change this method the class that contains it has to be
recompiled and redeployed
and any other classes that are dependent on this video coder again has to be recompiled and
redeployed
.
And as I've always said Suffer engineers.
We want to reduce the impact of change in our Soffer.
So earlier in the section I introduced we to the open closed principle of object oriented
programming
.
Just to refresh wer memory.
Open Closed principle or OCP states that Soffer entities should be open for extension or
closed or modification
.
Now we are not going to apply this principle everywhere but there are areas in our system
where we see
there is potential for change like in video and Khoder.
We know that potentially we could send a text message to the user.
Or maybe it would notify them as they are online on the Web site.
So here is an area that is going to be affected as a result of that change.
Now how can we implement open closed principle using an interface here.
Well first of all when we design this class we should not think about mail service.
We should think in abstractions.
We should think when we do in court it does its job.
It needs to send a notification to the user who owns the video how we don't know we don't
know what
kind of notification.
We don't know if it's a mail or text message or a real time notification.
So video encoder should not know about that.
So in this class we need to think of a notification channel as an abstraction and that's where
an interface
comes in because the interface is just a role is a contract.
Again remember the example about a restaurant and a chef a restaurant and the chef.
Anyone who can fulfill that role based on some standards can be a chef for that restaurant.
We don't want the restaurant to be tightly coupled to John or Steve so Same here.
We don't want the video encoder to be tightly coupled to a mailed notification service.
So let's see how we can use an interface to implement open closed principle here.
First we define an interface let's call it.
I notification channel.
Again this is an abstraction.
We're not talking about mail or text or whatever.
Now this is just a notification channel.
We want to send a message to that channel.
So here we need a method like void Sandt which gets the argument type message.
Let me create this class
so I moved this class to a separate file
back to where we were.
And same for notification Channel
8 or so it's a very simple clean interface.
Now mail could be one notification channel or H.M.S. could be another notification channel
so we can
create concrete classes that implement this interface so let's create a new class here.
Mail notification channel implements notification channel
alt and enter.
So for simplicity let's just log a message on the console saying sending mail.
It moved this class to a separate file back to where we were.
Let's create another class that implements this interface this time as a mass notification
channel notification
channel.
Again the same steps implement the interface log and message on the console saying sending
asset mass
.
We put this in a separate file
area so we have one interface with two implementations.
Now let's go to our video encoder class.
So here we no longer need a reference to mail service.
We should think in terms of a notification channel but we could have more than one
notification channel
.
Right.
Because at the same time we may want to send an e-mail and also a text message to the
person who owns
the video.
So what I'm going to do is let's remove this field here.
Basically we need a list of notification channels.
So private read only by a list of I notification channel and let's call them notification
channels.
Now resharpen is detecting that I'm using I-List and that's a generic interface as defined in
system
dot collection dot generic so we can click that or press enter so it as the using statement on
the
top here.
Again if we don't have the sharper We have to manually type that.
Now in the constructor we need to initialize that list.
So let's just initialize it to an empty list.
The list of notification channels.
Now all we need to do here is once the video is encoded we need to iterate over the
notification channels
and notify each of them.
So we do a simple for each for each channel in notification channels channel that send a new
message
.
Right.
So in the video encoder we are not talking about Meltzer's we're not talking about S.M. Yes
we're talking
about abstractions.
I notification channel whoever implements that.
That's none of our business.
We don't code or is not going to be affected.
We can create new implementations of that interface and this class remains unchanged.
So with this we actually have open closed principle.
Our software is open to extensions.
We create new implementations of I know to be Kishan channel and it's close for
modification.
So this class is no longer going to be changed.
Now it's just one step missing here.
We need to tell video encoder about the actual notification channels at runtime.
So how we do that is because this list is defined as private because its implementation detail
of this
class and we don't want to expose it to the outside.
We need to create a method here the public void let's call it register notification channel.
We simply guess.
And I notification channel parameter and call it channel.
All we do here is we add that to our list and add channel.
So this is the method we use from the outside.
Let's go to the program class.
So the main method after re-initialize encoder we call that register notification channel
method and
here repassing a concrete implementation of notification channel.
So new mail notification channel and we repeat that it's time we use a mass notification
channel.
Now let's run the application.
There we go.
We got two messages.
One is sending mail.
One is sending S.N. mess.
And interestingly we can create a new class that implements I notification channel and we
just passed
that here in the main.
And as we saw video encoder is not going to be affected.
Now the interesting thing here is that with interfaces we have a polymorphic behavior.
Let's go to video encoder.
So when we are rating this notification channels list at runtime when we call the Send method
depending
on the runtime type of that notification channel a different method is going to be called.
And that's what we call polymorphism.
So at runtime if the first element of our list is a mail notification channel object the Send
method
in the mail notification Channel class will be called upon Get back here.
Now if the second element of the list is an s.m.m notification channel object a different Send
method
will be called upon.
So as we see with interfaces we can have polymorphic behavior and that's very powerful.
Now there is also a different way to implement the exact same scenario in C-sharp and that is
using
events and delegates.
And that's something that I have classified as advanced topic which we can find in my C-
Sharp advanced
course.
So in my C-Sharp advanced course I introduced we to the concept of delegates.
And I actually have a video on my WeTube channel called events and delegates where I
introduced the
exact same problem but use a different solution using an event and a delegate to implement
that kind
of extensibility.
So in case we're passionate about learning all this stuff that's an additional video we can look
at
.
I hope we enjoy this lecture.
And thank we for watching
ADVANCE

Hi! Thank we for taking the C# advance course.


My name is Mosh Hamedani and I'm gonna be wer personal instructor in this course.
In this course, I'm gonna take wer C# skills to advanced level.
I'm gonna teach we the language features that we
need to know in building real world applications.
Whether we want to build mobile apps, desktop apps,
or web applications, we're going to be using these features all the time.
Features like LINQ, Lambda Expressions, Events, Delegates,
Extension Methods, Nullable Types,
Generics, Exception Handling, and so on.
I hope we enjoy watching this course. And let's get started.

Hi guys, my name is Mosh Hamedani.


And in this video, I'm going to talk about C# Generics.
Before we start with generics,
let me explain what problem generics came to solve.
In.NET version one, we didn't have generics.
So let's say we wanted to create a list to store a list of numbers.
This is a simple and basic implementation of a list.
We could have a method called Add to add a number to the list,
and an indexer that returns the number at the given index.
Now of course there are more methods like Remove and Find,
and I'm just leaving that for simplicity here because
the intention is to talk about generics and not data structures.
Now, if we wanted to store books in a list,
obviously, this class wouldn't work.
So, we had to go and create a class like this,
call it BookList with a method called Add,
a parameter called book, and similar indexer.
Now the problem here is, for every type,
we have to create a separate list,
and this is a lot of code duplication and not productive.
Plus, if there is a bug,
we have to fix it in multiple places.
So one solution to fix this is to use a list of objects, something like this.
But the object, because the object is the parent class for every type in.NET,
we can easily pass any types to this method here or get any object from this indexer.
But there is another problem here.
The problem is performance.
If we use this class for storing value types like integers,
every time we insert a value type inside this list,
it has to be boxed – to be stored as an object.
And every time we access that value,
it has to be unboxed,
and this has a performance penalty.
Or even if we use reference types,
every time we want to cast an object,
let's say a book, to an object or vice versa,
this casting, again, has performance penalty.
So generics came as a solution to solve this problem.
With generics, we create a class once and reuse it multiple times;
and it doesn't have the performance penalty like with the ObjectList here.
So let's see how we can create that generic list.
Let me get rid of this code here.
So I'm going to create my generic list,
next to this one so we can see the differences.
We start with public class.
I call it generic list.
Now generics have a parameter and
the parameters are specified with angle brackets. So like this.
And we usually call them T as in short for template or type.
Now we create our Add method.
Now instead of getting a book here we would get a T. What is T?
We don't know yet. The consumer of
this class will specify that. I will show we in a second.
Similarly, to get the object at the given index,
We return T.
So that's all we have to do.
Now let's see how we can use that.
We go to our program.cs.
So here we're extensioning a book object,
we're extensioning a list of numbers as we see,
and we're extensioning a list of books.
Note that the problem here is that we have two different types of lists.
We can simply use our generic list instead of these two classes here.
So I can actually comment out this piece of code.
Now let's create a list of numbers.
I use the generic list and here I specify the type of T that will be a specified earlier.
So in this case we want a list of integers.
So I'll put it here.
And now when I access the Add method,
note that the parameter is of type integer.
We can use the same generic list to store a list of books.
So I suppose if I book as a template parameter and say books then add.
No, the Add method gets an object of type book.
So a new book, blah blah blah.
So see, we get code reusability and we don't have that performance penalty.
Why? Our runtime, our generic list is actually a list of books.
It's not a list of objects.
So there is no casting or boxing.
So this is the basics of creating a generic list.
Now in practical terms most often we will be using generics as opposed to creating ones.
In fact I personally in my professional career as a.
NET Developer have very rarely come
across situations that I had to create generic classes or to generic methods.
I would say maybe three or four times over the course of a few years.
Most often we will be using the generic lists that are actually part of.
NET. So we're not going to create a generic list.
In fact let me show we where all the generic collections are in.NET.
So we go to System.Collections.Generic.
And look here we've got a bunch of classes like Dictionary,
HashSet, some interfaces like ICollection IDictionary, IEnumerable,
which is pretty popular, IList,
LinkedList, List, which is like our generic list,
Queue, SortedList, Stack and so on.
But in case we need to create a generic for the application we're working on,
the rest of this video I'm going to cover more details about creating generics.
So let's get back to our generic here.
See here T is a parameter.
We could have multiple parameters.
For example, a use case of that is for dictionaries.
A dictionary is a data structure that uses a hash table to
store and retrieve objects which provides
a very fast and efficient way to access objects.
So with a dictionary,
we need to specify a key and a value,
and they can be of any type.
So let me create a dictionary here.
Public class generic dictionary.
So I want a key here and a value.
Note that I'm prefixing them with T and giving a proper name
here like this is the template parameter
for key and this is the template parameter for value.
I have seen some developers use something like T,
U or V here which actually makes no sense in terms of code readability.
So always prefix wer generic parameters with T and then give it a proper name.
So in this case our dictionary has two parameters,
T key and Add T value.
Our Add method would look something like this,
Tkey key, TValue value.
Now to use that,
we can go back to our program.cs.
Let me create a dictionary here, generate dictionary.
I want my keys to be of type say string,
and values can be of type book.
This way I can call the Add method and note that
the first parameter is a string and the second is a book.
So I can say 1234,
and I'm going to store this book here, just like that.
Another thing we need to know about generics is constraints.
Look, in this case our generic list here or generic dictionary,
any type can be passed here.
There is no limitation.
Sometimes this is good like in terms of list,
we probably want to store a list of anything and everything.
So there is no need to apply constraint.
But sometimes we would want to limit what is being sent here.
Let me walk we through some examples.
So back to our program.cs Here.
And we use Resharper to put it in a separate file.
Okay, let's say we would like to create a method that gets two parameters,
let's say two numbers, and returns the bigger one.
So typically this is how we do it.
So if A is bigger than B,
we return A, otherwise we return B.
Now if we want to create a generic version of that, this is how we do it.
So public, instead of returning int return T,
and the name of the method.
Here we add the template parameter.
And of course both of our parameters are going to be of type T,
so T a and T b.
Now see, if I write the exact same code, it's not going to work.
Why? Because at this time,
the compiler doesn't know the type of T,
so it cannot apply a comparison between a and b.
At this point it thinks a and b are both objects.
Let me show we that.
So these are the methods that are available in a,
which come from the object class.
So what we need to do here is,
we want to assume that both A and B implement
the comparable interface which provides a method called compare to.
And with that we can compare these two objects.
So that's a use case where we need to apply a constraint.
We apply a constraint by going here at the end of the method and saying where T,
we use colon, as it is IComparable.
With that, if I say a., see,
we get a new method here CompareTo,
which comes from IComparable.
So with that we can say,
if a compared to b is greater than zero,
return a, otherwise return b.
Also note that here I created
a generic method inside a non generic class and that's perfectly fine.
So we don't always have to start with the generic class.
We could potentially move this template here to the class level.
So utilities for T,
where T is IComparable,
and then we don't have to repeat that here.
We can just get rid of that, just like that.
Okay, now that we have an understanding of constraints and why we need them,
let me show we the other types of constraints.
Here are five types of constraints.
We can say where T is IComparable,
as in applying a constraint to an interface or we cannot apply constraint to a class.
In this case we are saying,
if T is a product or any of its children any of its subclasses,
we can say T should be a value type,
so we use the keyword struct or we could
say where T is a class as in it has to be a reference type.
Or we can say where T is an object that has a default constructor.
Now don't worry, I'm going to walk we through these with examples.
So, so far we have seen a constraint to an interface.
Let's take a look at a constraint, the class.
So I create a new class here,
public class a DiscountCalculator,
T product, where T product is a product.
I'm going to move this to a separate file.
So in that case I can create a method here,
let's call it calculate discount,
which gets a parameter of type product or any of its subclasses.
And here look, we get the price and title attributes or property.
Earlier I created this product class.
Let me show we.
So this is my product class.
We have a title and a price.
We also have a book class here.
That derives from the product and adds an extra property here called ISBN.
So with that constraint when we say T product should
be a product or any of
its subclasses we have access to all of its properties or methods here.
Now we don't really care about the actual calculation of the discount.
But we've got the point.
Let's see an example of a constraint to a value type.
So public class Nullable T,
where T is a value type.
Let me move that to a separate file.
Okay, what is this used for?
Well in C#, as we know,
value types cannot be null,
so an integer should have a value like 0 1 2 3. It cannot be null.
We can use this class to give our value types the ability to be Nullable.
So let's create a constructor here.
Let's say in a constructor we can get;
we can get a value,
and in this class I'm going to store it as an object because I want it to be nullable,
so private object value.
And here let me initialize it with resharper we can press Alt and enter here and enter.
And it automatically initializes
my private field with the value passed in the constructor.
Now I want this class to have a property called HasValue.
So if my object has a value it returns true.
Otherwise if it's null, it returns false.
Get return, so if value is not null, return true.
And we can have a method called public which returns T, GetValueOrDefault.
So with this method, if our object is initialized,
let's say we have a number that is set to 5,
it returns the value which is 5.
Otherwise it returns the default value for that type.
So for integers it's 0.
So what we need to do is we say if it HasValue, then return value.
Then we just have to cast it because it's value here is of type Object, right?
But this cast is perfectly fine and it's safe
because that's what we are passing here in the constructor. We're storing it in here.
It's basically being boxed to be stored in the object.
But here we are un-boxing it and that's perfectly fine.
Now what if it's not set? What if it's null?
We need to find the default value for that type.
How do we do that?
We use the default operator.
So we say return default of T. So default is a good keyword that we need to know.
Now with this class,
what we can do is we can go ahead and actually,
I forgot to create a default constructor here in case the value is not set.
Now let's go to our programs,
yes, and use that.
I'm going to clear everything here.
We don't need them anymore.
So I can say, var number equals new Nullable of int.
I can give it a value like five.
Let's lock something to Console, so.
CW, it's a code snippet, press tab.
I would say Has Value,
plus number that HasValue, Console WriteLline,
and the actual value is plus number.GetValue or default.
Let's run this code.
So note that, yes it has a value and its value is set to 5.
Now we can use this class without setting a value.
In this case we have a nullable integer.
So let's run this again.
So it has a value.
No, what is the default value?
It's zero. Now, we don't really have to go and create this nullable class.
It's actually part of.NET framework.
We can find it in System.Nullable, is defined here.
And in fact it's structure. Look at this icon here.
It's not a class.
So let's go here.
So this nullable is using a constraint to specify that T has to be a value type.
Let's look at another example.
Let's go to our utilities class here.
Let me create another method here,
public void DoSomething with T. Now let's say in some specific scenarios we
want to instantiate an instance of
T. So if we want to create an object we want to do something like that.
But that doesn't work because at this time
the compiler doesn't know exactly what type T is referring to.
All it knows is that T should implement IComparable interface.
If we want to instantiate t here we need a default constructor, right?
So what we can do is to apply a second constraint here.
We can separate constraints with the comma.
So to add a constraint to a default constructor that's what we use.
Now this is perfectly fine.
So with constraints we can specify that T must implement a given interface or B of
a given type or any of its subclasses or be
a value type or a reference type or have a default constructor.
I hope we enjoyed this video and thank we for watching.

So what is a Delegate?
A Delegate is an object that knows how to call a method or a group of methods.
A simpler way to define that is a Delegate is a reference or a pointer to a function.
Now why do we need something like that?
We can call methods directly.
Why do we need a Delegate that is responsible for calling methods for us?
Well, this technique allows us to create applications that are extensible and flexible.
And often this is used in designing frameworks.
Let me explain this in code.
Here in this project, I have a class of photo that represents a photo or an image.
A Photo Processor, which has one method called Process.
It takes a path to a file, loads the photo,
applies a set of filters like brightness,
contrast, and resizes the photo.
Let's take a look at the Photo Filters.
For simplicity, I have just used Console.WriteLine
because we don't want to get distracted with image processing algorithms here.
But the point here is imagine we're responsible for
designing a framework that is used for processing photos.
This code has a problem. It's not extensible.
What do I mean by that?
Well, look, so far we have applied three filters here.
What if we release this framework,
but another developer wants to use wer framework
and apply a new filter that we haven't defined?
Then the problem is we have to create that filter and recompile and redeploy wer code.
Now imagine if every time a developer in the world needs a filter,
we have to keep compiling and deploying wer code.
This is not a good idea.
So with Delegates, we can make this framework extensible
such that a developer can create their own filters without relying on we.
The same problem can be solved by Interfaces using some kind of polymorphism.
But in this video, I'm going to show we how to use Delegates to achieve this.
Later, I will give we a simple guideline to choose
whether to use Delegates or Interfaces.
So before we change anything in this code,
let's run the application and see what happens.
So we got three messages on the console: applying brightness,
contrast and resizing photo.
How do we use a Delegate to make this extensible?
First, we need to define a Delegate type.
So we start with public Delegate.
When defining Delegate we need to define the signature of the method.
Now this Delegate will be responsible for calling.
So that's a void.
And I'm going to call it PhotoFilterHandler.
It takes a parameter of type Photo and that's it.
So this is the name of our Delegate.
And an instance of that Delegate can hold
a pointer to a function or a group of functions that have the signature.
So they're void and take a parameter of type photo.
Now to make this method extensible,
instead of hard coding this filters here,
I'm going to get rid of that and pass a Delegate to this method.
I'm going to call it here passing our photo object.
What this means is this code does not know what filter will be applied.
And it's the responsibility of the client of this code.
Whoever is using that,
they will define the filters they want,
maybe a developer wants to apply only brightness and contrast,
maybe another developer wants to apply 10 other filters.
It's up to them. This framework does not have to be recompiled and redeployed,
which makes it extensible.
Now, the client of this class is our program.cs.,
and imagine this is the code that we as a developer
or a consumer of that framework is writing.
So here first we have our photo processor instantiated.
Now let's create an instance of that Delegate.
So our Delegate is PhotoProcessor.
I defined it in that class and it's called PhotoFilterHandler.
So filterHandler equals I'm going to point it to a method.
What method? Well, we can start with this PhotoFilters.
Let's assume that this was really with the framework.
So let's say we want that Delegate to point to this method first.
I create an instance of photo filters,
filters equals new PhotoFilters.
Right now my handler which is a Delegate or pointer to a method is going to point to
filters.ApplyBrightness and in our process method
we pass this filterHandler here.
So now if I execute this code, let's see what happens.
We get Apply brightness.
We can easily change this code and apply another filter.
So we get the Delegate here and we use the plus equal operator to add another filter
or another pointer filters.ApplyContrast.
Let's run the application again.
Look now we've got two filters.
And what is interesting is that
if I need a filter that was not released with the framework,
I can create my own here.
Let's say, I would like to create a filter for removing red eye,
static void RemoveRedEyeFilter.
It takes a parameter of photo.
So this method should confirm with the signature we defined here or our Delegate.
So again a Delegate is a pointer to a method with a signature.
I can reprogram. So this is my custom filter.
And here I'm going to type in Console.WriteLine Apply RemoveRedEye.
I can go ahead here and add that to our Delegate.
We'll Remove RedEyeFilter.
Let's run the application.
There we go. We got the new filter here.
So Delegates are very powerful and it allows us to
create applications or frameworks that are extensible and very flexible.
Again we saw that I added this new filter here,
but that class PhotoProcessor was absolutely unchanged.
So was the Photo Filters that were released with the framework.
Now let's get back to our program.
I want to show we what happens under the hood when we create a Delegate.
So I'm going to put a breakpoint here with
F9 and press F5 to run the application in the debug mode.
OK. Let's see I can make this filterHandler variable.
Look it derives from multicast Delegate class.
So every Delegate in.NET that we create with the Delegate keyword is essentially a class.
A class that derives from multicast Delegate. Let's expand that.
So that class multicast Delegate is derived from system to Delegate. Let's expand this.
This Delegate class has two public properties, Method and Target.
Method represents a method that the Delegate is pointing to.
So in this case, we set our Delegates to point to
ApplyBrightness method of Photo Filters class.
So Target is the class.
That holds that method.
Now let's continue execution one line.
So F10. Let's see what happens.
Filter Handler and expand that here.
Because it derives from multicast Delegate that means we
can have pointers to many functions,
which in this case, we have two functions or
two methods ApplyBrightness and ApplyContrast.
Let's take a look. So if I expand multicast Delegate in the nonpublic members,
it has a field called invocation list.
Let's expand that. So it has two methods.
One is ApplyBrightness.
One is ApplyContrast.
So the difference between multicast Delegate here and Delegate is that multicast Delegate
allows us to have multiple function pointers where
as Delegate allows us to have only one function pointer.
So in this case, because we are appending multiple filters,
multiple function pointers to our Delegate,
our Delegate is a multicast Delegate.
OK let me stop the debugger.
OK now we have an understanding of what Delegates are and what we can do with them.
Let's go back to our PhotoProcessor code here.
See here we defined a custom Delegate that points to a method that
returns void and takes a parameter of type Photo.
Instead of creating a custom Delegate,
we could use one of the existing Delegates that come in.NET framework.
In.NET we have two delegates that are generic and they are Action and Func.
Let me show we how they work?
System.Action.
So Action as we see from the icon here is a Delegate.
It comes in two forms.
One is non-generic, and one is generic.
Let's look at this one. Look, it has 16 overloads.
One, that takes only one parameter.
Here is another one that takes two parameters,
three parameters and up to 16 parameters.
So this Action can point to a method that takes any of these parameters.
A method that takes one parameter or up to 16 parameters.
We have another Delegate which is Func. Let's take a look at this one.
The difference between Func and Action is Func points to a method that returns a value,
rather Action points to a method that returns void.
So in this case, look, the first overload of Func specifies
out TResult and that is used to specify the return value from that method.
If our method has one parameter and returns a value we can use
this overload or if our method has
two parameters and returns a value we can use this one.
So all these 16, 17,
maybe 18 overloads gives we a lot of
flexibility which means we don't need to go and create wer custom Delegates.
So let's change our application a little bit.
I'm going to get rid of this PhotoFilterHandler and instead use
the generic Action Delegate.
So in the Process method,
we say we can pass any Delegate
that takes a Photo as an argument and returns void.
Let's run the application. We had an error here which is saying
the type name PhotoFilterHandler does not exist in the type DelegatesPhotoProcessor.
So here I forgot to change that.
Here instead of using the custom Delegate,
we used Action of Photo.
Let's run the application.
All good. So to recap,
a Delegate is a pointer to a function or more
accurately it's an object that knows how to call a method or a group of methods.
We use Delegates to achieve flexibility and extensibility.
Of course, we don't need this all the time,
but if we're designing an application or
a framework where extensibility or flexibility is a concern,
we can use Delegates for that.
Alternatively, we can use Interfaces.
How do we decide whether we need to use
an Interface or a Delegate to achieve flexibility?
Well, part of that is personal preference and different developers have different tastes.
But the guideline in MSDN suggests to use Delegates when we have some kind of
eventing design pattern or the caller doesn't need to access other properties,
methods, or interfaces on the object implementing the method.
In the case of the example I showed we our filters were
just one basic simple method and there were no other properties or methods.
But imagine if our Photo Processor needed to access other properties or methods,
obviously a Delegate wouldn't work and we have to use an Interface.
Well that's it for this video.
I hope we enjoyed it. And thank we for watching.

So lambda expressions.
What are these lambda expressions?
A lambda expression is nothing but an anonymous method.
That is a method that has no access modifier,
like public or private,
and has no name,
and it has no return statement.
Why do we use them?
Why do we use anonymous methods? For convenience.
We can write less code and achieve the same thing,
plus our code would be more readable.
Let me show we this with an example.
Let's say, we would like to write a method that takes
a number and returns a square of that number.
Typically, this is how we would do this.
So static and square and number.
Return number times number,
it'll return the square of that number.
Let's make a call to this method.
First, I put Console.WriteLine(Square),
I'll set five here,
so we should get 25.
Let's run the application with control and F5. There we go.
Now, with lambda expression,
we can achieve the same thing but with less code.
Let me show we how it works.
The syntax for a lambda expression is something like this.
So we have the arguments,
and the lambda operator, and some expression.
Read this as, args goes to some expression here.
For example, if I want to rewrite this method,
using a lambda expression,
this is how I would do this.
So the parameter or the argument is number,
then goes to number times number.
So this is what we call a lambda expression,
and this code is exactly equivalent to this method.
And as we see it's shorter,
I didn't have to specify static,
an access modifier like public private,
and as the return type or as the argument type.
The compiler can automatically infer that in most cases.
And if not, we can explicitly specify that.
I also didn't have to write this return statement here.
So what we need to do is we need to assign that to a delegate.
Remember what a delegate is?
A delegate Is a pointer or reference by a method or a group of methods.
In.NET, we have some built-in delegates that we see all the time.
For example, we have Func<> and Action<>.
Just to refresh wer memory,
let me comment on this a bit.
So Func<> represents a method that takes
zero or more arguments and returns a value of type TResult,
which is generic, as we can see here.
Action<>, on the other side,
is another delegate that takes zero or more arguments and returns void.
In this case, if we want to use a delegate to point2,
this method here we need Func<>.
So we can say, Func of int and int.
The first parameter here,
the first generic parameter here,
represents the argument to the method;
and the second one represents the data type or the return value.
So in this case, because our square method takes an integer and returns an integer,
we use Func of int and int.
So let's give it a name.
This delegate, as we see,
can point to this method without any problems.
Now, what they can do is instead of creating that method here,
I can just use a lambda expression here.
Saying, number goes to number times number and I can call this delegate like this.
Let's run the application.
We get the exact same result 25.
So there is no need to write this method here.
I can just get rid of it, which would be sharper.
As we see it's grayed out,
so I can press Alt and Enter.
And note the first suggestion is "Remove unused method".
So enter, done.
So this is the basic syntax for a lambda expression.
On the left side, we've got the arguments,
the lambda operator, and the expression.
If we don't need any arguments,
we need to write a lambda expression like this goes to, and here is the code.
If we have one argument,
we can use just the argument by itself without using parentheses.
And if we have multiple arguments,
we should always surround them in parentheses (x,
y, and z) goes to blah blah blah.
In terms of scope,
the lambda expression here has access to all the arguments passed,
as well as any variables defined inside the method here,
where we define the lambda expression.
So, let me show we an example.
Let me delete this, I'll create another one.
Let me define a constant,
call it factor, give a value of five.
I want to create a method that takes a number and multiplies that by this factor.
So I can use Func<> delegate,
the input to that function would be an integer,
and it returns an integer.
I call this function or delegate, multiplier,
and I use a lambda expression to say,
"n goes to n times factor."
So as we see, we have no compile-time error here.
This lambda expression perfectly understands this factor,
constant that is defined here,
inside this method, as well as the argument that is passed to it.
So let me call this multiplier.
Multiplier. We had a value of 10,
so we should get 50 in result.
And I can put that on console, so cw, remember?
Code snippet. Tab, result,
and lets run the application.
There we go, we got 50.
So, this is the basic of lambda expression.
But let me show we a more practical and common use case of lambda expressions.
First, let me get rid of everything here.
We're going to work on another example.
Here, I've got a class, called BookRepository.
Let's say this is responsible for returning the list of books from the database.
Now, to keep things simple here,
I have just hardcoded a few book objects in a list.
So, this method here get books,
returns a list of books, and list.
As we see, it's a generic type,
as indicated by angle brackets.
So it's a collection of books.
And here, I am using the object initializer syntax during initialization of the list,
so I can immediately populate that list with a few objects as I instantiate each book.
Again, I'm using the object initializer syntax to quickly initialize the book object.
So we have three books.
Title one, two, three.
The first two are less than $10 as we see,
and the second one is $17.
Let's say, we want to write the code that
returns all the books that are cheaper than $10.
So, let me show we how we would typically do this without a lambda expression,
and then, we'll refactor the code and use a lambda expression instead.
So first, let's get the list of books.
So, at this point, our books variable is of type, list of book.
So here, as we see in the tool tip,
It points to a list of T,
and here note that T is a LambdaExpressions.Book.
Lambda expressions is the name of my solution or project,
so it's a namespace.
Okay, now, let's take a look at this object.
See, here, in the list,
we have these fine methods here that are used for filtering collections.
I'm going to show we how to use FindAll.
Take a look at the argument.
Here, we need a predicate of type book.
What is a predicate?
We see that all the time when working with collections.
A predicate is basically a delegate which
points to a method that gets a book, in this case,
because it's of type of book,
and returns a boolean value specifying if a given condition was satisfied.
Let me show we an example.
So I'm going to create a predicate function.
Let's call it IsCheaperThan10Dollars.
I pass a book here,
and I return True if book.Price is less than $10.
So this is what we call a predicate method.
It gets an object of type book,
and returns True if a given condition is satisfied.
All these Find methods here,
they accept a predicate.
Look, so, what happens when I call this method and pass a delegate of type predicate?
Which means a method like this,
I can pass that here,
is cheaper than $10.
What happens is, the code inside this method,
well iterate the collection,
and for each book,
it will pass that book to this method to determine if the condition is satisfied.
If yes, then it will return that book in the list of results.
So, with that code,
I can say, cheapBooks equals to that.
And let's iterate that to our collection.
It should be cheapBooks.
And let's put that on the console.
So I'm going to display the title of the book.
Let's run this application.
So we got Title one and Title two,
and back to our BookRepository,
note that all of these are under $10. So the code is working.
Now let's see how we can change this code and use a lambda expression.
See the problem here is every time we want to call this Find or any of its variations,
we have to go and create a method like this,
and while this is perfectly fine we can achieve this with less code.
So why not? So here,
all we have to do is to say,
book goes to book.Price is less than 10.
So, this lambda expression is exactly equivalent to this method here.
And with ReSharper installed in my Visual Studio,
we can see that now this method is grayed out,
which means it's not used.
So what I can do is to put my cursor on the method name here,
and we get this triangle here.
I can press Alt and Enter.
And the first suggestion is to remove unused method.
So I press Enter,
and that code is gone.
So again this is a lambda expression.
On the left, we've got the argument,
and on the right side, we've got the actual expression.
And this is what we call a lambda operator.
We read this expression like this,
book goes to book.Price is less than $10.
In C#, it's pretty common
to use a single letter when defining lambda expression arguments.
So in this case, because we are working on books, it's obvious.
So, we can just use b.
See, the code is even shorter now.
Well, that's it for this video.
I hope we enjoy it, and thank we for watching.
Hello everyone. welcome to programming with Mosh.
My name is Mosh Hamedani and in this video,
I'm going to talk about events and delegates in C#.
I have noticed that a lot of developers starting with C#,
find the concept of events and delegates a little bit confusing.
In fact, I was one of them when I was starting out.
So, I decided to create this video for we and I hope,
by the end of watching this video,
we will have a good and in-depth understanding of events and delegates,
why we need them, how to use them, and how to create them.
So let's get started.
So, what are events and why do we need them?
Well, events is a mechanism for communication between objects.
That means when something happens inside an object,
it can notify other objects about that. Why do we need that?
Because it can help building loosely coupled applications.
What is loosely coupled applications?
That means an application,
that its components or classes are not tightly coupled together.
A loosely coupled application is easy to extend without
breaking or changing one or more of its existing capabilities.
Let me show we an example of this in the code.
So take a look at this class.
This is a video encoder class with one method,
called encode, which encodes the video that is passed to it.
For simplicity, I've gotten rid of the encoding logic, but look at the last line.
Here, when the encoding is finished,
we use the mail service to send a mail message to the person that owns the video.
Now, there is nothing wrong with this code,
but let's say, in the future,
there is a scenario and we may want to send a text message to the video owner.
So what we need to do is to go ahead and add this extra line of code to this method.
Now, again, this is for simplicity.
In a real world scenario,
it could be a few more lines of code.
Now, the problem here is,
because we add this extra line of code here,
that encode method is changed,
which means it has to be recompiled,
which means the video encoder class also has to be recompiled,
which means any other classes that are
dependent on this video encoder have to be recompiled and redeployed.
So, as software engineers,
we want to reduce this problem.
We want to design our application such that when we want to change the application,
that change has minimal impact on the overall application.
The problem here with this code is that,
by adding an extra line,
we may accidentally break something along the way.
Now we can use events to resolve this problem.
Take a look at this picture here.
We can have our video encoder class to publish an event called VideoEncoded,
and have the MailService class to subscribe to that.
In this case, we refer to VideoEncoder as a publisher or an event sender,
and MailService is a subscriber or an event receiver.
Now, what is interesting about this picture?
That VideoEncoder knows absolutely nothing about MailService,
which means, in the future,
if we want to extend our application and add
the capability to send a text message when the video is encoded,
we can simply create a new class, called a MessageService,
and have it subscribe to that VideoEncoded event of the VideoEncoder.
So basically, the VideoEncoder does not need to be recompiled and redeployed,
and we simply extend the application by adding a new
class-- so this reduces the impact on the application.
Ideally, if we could extend our applications by simply adding new classes,
the compilation time would be reduced and
application could be redeployed without breaking things along the way.
Now, let's take a look at what the code would look like if we want to
implement this eventing mechanism between these classes.
So here is our VideoEncoder class again.
We have the encode method as before,
with the encoding logic at the end.
Instead of directly making a call to the MailService,
which we had before, we simply call a method called OnVideoEncoded.
Don't worry about that method,
I'll cover it shortly,
but the purpose of this method is to simply notify the subscribers.
VideoEncoder knows absolutely nothing about the MailService or the MessageService;
they can come later and we can add
more subscribers without changing anything in this code.
Now back to our picture, we might be wondering.
How does the VideoEncoder notify its subscribers?
Well, for video encoder to notify its subscribers,
it needs to send a message to them.
In practical C# terms,
that means invoking a method in the subscriber.
But how does the video coder know what method to call?
For that to happen,
we need an agreement or a contract between these publishers and subscribers.
So this agreement is something that both the publisher and subscriber agree upon.
That is a method with a specific signature. Take a look at this method.
So this method is void.
It has two parameters,
which the first one is an object and the second one is an EventArgs,
and this is a very typical implementation of a method in the subscriber.
We often call these methods event handlers and that's the method that
is called by the publisher when the event is raised.
So that means, back in our picture here,
we need to have a method like that in MailService and MessageService.
So, when the VideoEncoder wants to raise that event,
it's going to call these methods.
Now, I need to clarify something here.
Again, VideoEncoder does not know about the existence of MailService or Message Service.
It knows absolutely nothing about them.
It's decoupled from them.
All it knows is a method, nothing else.
Now, how do we tell VideoEncoder what method to call?
That's when a delegate comes in.
So, a delegate is basically an agreement or a contract between publisher and
subscriber and it determines the signature of the event handler method in the subscriber.
So, back in our picture here,
we can have a delegate that determines when a video is
encoded and we want to notify subscribers,
we should have a method that is void with these parameters.
The name doesn't matter but the signature is important.
So now that we have a basic understanding of events and delegates,
let's take a look at a piece of code and see how to create an event and a delegate.
So, here I've created a very simple console application.
Let me walk we through the classes we've got here.
First, we've got a video class which is a very basic class with
a simple property for the title of that video.
We also have that video encoder that we saw earlier in the slides.
So it has one encode method that gets the video.
First, it logs a message on the console saying we are encoding
the video and just to simulate an encoding process,
I used thread.Sleep to delay the application for a period of three seconds.
In the program.cs, in the main method,
first we instantiate the video here,
then we instantiate the video encoder and finally we call the encode method,
passing the video object.
So, very basic. Let me run the application now so we control and f5.
Okay, we got the message Encoding Video, and notice,
there was a three second delay before we saw the,
Press any key to continue. Let me run it again.
So waiting one, two,
three. There we go.
Okay, now, we want to implement an event
in the video encoder such that when the encoding is finished,
it notifies anyone who is interested in that event.
Now, to give this class the ability to publish an event,
there are three steps we need to follow.
First, we need to define a delegate,
that is, the contract or the agreement between the publisher and the subscriber.
So, a delegate determines the signature of
the method and the subscriber that will be called when the publisher,
in this case video encoder, publishes an event.
Second, we need to define an event based on that delegate.
And third, we need to raise or publish the event.
So, let's go ahead and implement each of these steps here.
To define or declare a delegate,
we start with public because we want it to be accessible
anywhere and we use the key word 'delegate'.
Now, imagine we're declaring a method.
To declare a method,
we need to specify the return type,
give it a name and parameters.
And this method will be actually the event handler and the subscribers.
So, if I want to declare an event,
I would say void or give it a name, VideoEncodedEventHandler,
then parameters typically in.NET,
we have this convention that we want the first parameter of the event handler to be
an object and that is the source of
the event or the class that is publishing or sending the event.
And the second parameter is in EventArgs,
which is basically any additional data we want to send when the event.
So, let's review up to this point.
We are declaring a delegate,
which actually holds a reference to a function that looks like this.
So that function or method is void.
It has two parameters.
The first one, typically in.NET should be of
type object which is the source of the event.
And the second parameter is EventArgs,
which includes any additional data about the event.
Now, how did it come up with this name?
In.NET we have this convention and we say
if the name of our event is going to be VideoEncoded,
we use that and then append EventHandler as the name of the delegate.
So that is our first step, define a delegate.
Now we need to define an event based on that delegate.
So we start with public event.
This event should be based on that delegate.
So we use VideoEncodedEventHandler,
and give it a name.
So VideoEncoded.
Note that I use the past tense form here
to indicate that something has happened and finished.
Sometimes in.NET we may see an event referring to present tense like SameVideoEncoding.
In that case that event should be fired or
published before the encoding is finished, sorry, started.
So here we just use the past tense.
So the second step is done with define
an event called VideoEncoded, based on that delegate.
And the third step is to raise the event.
To raise an event we need a method that is responsible for that.
Let me create that here.
So in.NET again, there is a convention -.NET Framework
suggests that wer event publisher methods should be protected.
They should be virtual and void.
And in terms of naming,
they should start with the word on and then the name of the event, which is VideoEncoded.
So here in our encode method,
once the encoding is finished here,
we just need to call this method and
we're assuming this method will notify all the subscribers.
So how do we notify subscribers?
That is the responsibility of this method.
We start with checking if there are any subscribers to this event.
So we say VideoEncoded, if it's not null,
now we need to treat this as a method call,
that is, imagine we're making a method call here, so VideoEncoded.
To call methods we use brackets.
Now this method look at the parameters,
object source and EventArgs args.
That's the signature that we defined earlier here, all right?
So what is the source of the event or who is publishing the event?
The current class, or the current object, which is this.
And do we want to send any additional data with that event?
I would say for now just to keep things simple, I would say no.
So whenever we don't want to send any additional data, we use EventArgs.Empty.
This is a static property of this class which
returns an instance of EventArgs which is empty.
Later in the next step,
I will show we how we can send the actual video that was encoded.
So let's review the steps we have done.
First we defined a delegate which is here,
which determines the shape or the signature of the method in the subscriber.
Then the second step was to create an event based on that delegate.
So we defined the event here.
We are saying this event is called VideoEncoded,
and whenever we raise that we want
a subscriber with a method that confirms to this delegate, would be called.
And the third step is raising the event.
So in our encode method,
once we are done we call this method which by
convention should start with the word On and then the name of the event.
And it should be protected, virtual void OnVideoEncoded.
Inside this method we'll look at that event and if there are any subscribers there,
which means it shouldn't be null,
we're going to call them passing the reference to VideoEncoder and no additional data.
Now we are done here.
Let's go ahead and create a couple of subscribers.
So I'm going to go to program here.
Let me create a new class here, MailService.
So this class is responsible for sending an e-mail once the video is encoded.
Now I told we that back in our VideoEncoder,
when we defined this delegate I said we need
a method that confirms with that signature and the subscribers.
That method should be void and have these two parameters.
So let's go ahead in our Program.cs here,
in our MailService, create a method.
This is the event handler.
So that method should be void.
We're going to call it OnVideoEncoded.
We should have two parameters,
object source EventArgs e, right?
Now in this case we don't want to send an actual mail.
I just want to simulate that.
So we want to write a message to the console.
I'll show we a quick tip here. Just type cw.
That's a code snippet. If we press tab,
that just writes Console.WriteLine.
It's a way for we to quickly write code.
I have a course on Udemy called Visual Studio Tips and Tricks,
or Double Wer Coding Speed and in that course,
I teach we a lot of code snippets and various techniques to help we write code faster.
So in case we're interested the link is on the screen here. All right let's move on.
So when this method is called we want to log a message to the console saying okay,
we are in MailService sending an e-mail.
That's pretty much it. Now what we need to do is to subscribe
this mail service to the video encoded event of VideoEncoder.
So here in the main method we have the video,
we have the VideoEncoder, which is the publisher.
So that's going to be the publisher.
Let me create an instance of MailService,
MailService and this is going to be my subscriber, subscriber, right.
Now, before we call the encode method we need to do the subscription. How do we do that?
It's very simple. So we start with the publisher "VideoEncoder."
- look at this icon - that's an event, VideoEncoded.
So we are interested in that.
Now the notation is we use
the "+=" operator that is to register a handler for that event.
Who's the handler?
This method in the MailService,
this method in the MailService.
So I put that here,
MailService.OnVideoEncoded,
and semicolon.
Note that I'm not making a call to this method here so I don't have brackets here.
I just use the name of the method and basically what that means
is this is a reference or a pointer to that method.
So VideoEncoded event behind the scene is a list of pointers to methods.
When the video encoder wants to publish that event,
VideoEncoded, it looks at that list, here.
Here we look at that list, and if it's not empty,
that means someone has subscribed to that event which means we have
a pointer to an event handler method and then we're going to call that like this.
That's just the syntax in C#.
So let's get back to our Program.cs.
So note that again we need to do the subscription before calling the encode method,
otherwise the subscriber wouldn't be notified about the event.
Now let's run the application and see what happens.
So we got the Encoding Video which comes from the publisher and
then our MailService was notified and is trying to send an email.
Now let's look at some more interesting stuff here.
First of all I want to move this class to a separate file.
The slow way of doing that is to go here,
copy these and then go,
Solution Explorer, Create a new file and paste. It's not a good way.
What is a faster way?
There is a plugin called Resharper,
which is one of my absolute favorite plugins for Visual Studio.
With Resharper, we get this icon here,
and see, it's suggesting to move this to another file.
All we do is, we put the cursor here on the class name and then press alt and
enter and again we get the suggestions here, then press enter.
That's it. Resharper moved
that mail service class to a separate file which is MailService,
and added that to my solution here.
So Resharper really speeds up wer coding.
Again I explain this stuff in my Visual Studio course on Udemy,
so in case we're interested have a look at that course and we're going to love it.
Back in our program,
now let's create a subscriber that is responsible for sending a text message.
So I'm going to create another class saying MessageService,
and again, we want an event handler method here.
What is the signature of that method?
Should be public void OnVideoEncoded.
The first parameter should be object source,
and the second should be EventArgs args.
Again we want to simulate a texting scenario.
So just use cw Console.WriteLine,
press tab. There we go.
So we are in MessageService now,
"Sending a text message..." And then I go here,
alt and enter, and enter,
move that class to a separate file.
Now we can press control and hyphen to get back to where we were,
which is the program class.
So similarly, with NetPublisher and the subscriber,
now we can add a new subscriber,
var MessageService equals new MessageService.
So here is another subscriber.
By the way these comments is purely for educational purpose.
I'm not suggesting we to write comments like that in wer production code.
Okay, so we've got an instance of the MessageService.
We need to subscribe to the event just like before.
So who is the publisher?
VideoEncoder. What event are we interested in?
VideoEncoded. How do we subscribe?
Plus equal, now MessageService.OnVideoEncoded.
And again I'm not making a message call so there are no brackets here,
just a reference or a pointer.
Let's run the application again.
Look, we got the Encoding Video message which comes from the video encoder.
Then MailService was notified.
It's trying to send an email,
and also MessageService was notified,
and here it's trying to send a text message.
Now the beauty of this approach is
when I created a new subscriber which was MessageService,
did I change anything in the VideoEncoder?
Let's go here. My video encoder is exactly the same.
I didn't even make one line change,
and that's what I was telling we in the slides earlier.
So with events we can create
a publisher and we can add subscribers without changing the publisher.
So this code doesn't need recompilation and doesn't need to be redeployed.
And basically I can extend the application,
add more capabilities by simply creating a new class,
like in this case, MessageService.
Tomorrow we can have a new class,
call it, I don't know,
PagerService that sends a notification using a pager and nothing will be affected.
Now take a look at the VideoEncoder here.
Here we have a delegate which actually it's a reference to method,
or the event handler.
That method should be void and with these two parameters.
Now we want to send a reference to the video,
so the subscriber knows which video we encoded.
To do that instead of using EventArgs we need a custom class.
That custom class should derive from EventArgs and
include any additional data that we would like to send to our subscribers.
So let's go ahead and create that, and go here.
I call it VideoEventArgs because
it's a class that contains the data about the video that was encoded,
so it should derive from EventArgs.
Here we need to create a property that determines the video that was encoded.
So quick way of writing that is we type prop and then press tab.
This is a code snippet.
So now I specified the return type which is
video and the name I press tab again and enter, that's it.
So now we can change our delegate here instead of sending EvenArgs,
we send VideoEvent Args,
which means, here, see we got an error,
because when we are publishing an event we are sending EventArgs that empty whereas,
our delegate now expects a VideoEventArgs object.
So I'm going to go ahead and modify this.
We need to instantiate a VideoEventArgs.
And we also need to send a video, video equals,
but where is the video?
We don't have it here. But look,
in the encode video, I'm sorry,
in the encode method, when we encode
the video here we have a reference to the video object.
So we can simply pass that object to this method.
And of course we need to go ahead and change this.
But with Resharper, I can just press alt and enter and
see Resharper is suggesting to add that video parameter to this method.
So I just go ahead and there we go.
Now in the event publisher method,
we've got a reference to the video and I can just put that here.
So with this change now our publisher is going to
send some additional data which is encapsulated in that class,
VideoEvenArgs, and there we'll have a reference to the video that was encoded.
Now let's go to MailService.
We need to change this method to comply with that delegate.
So instead of EventArgs we want VideoEventArgs, right?
And then now what we can do here,
we can just we can output the title of the video.
So I would say "e.",
and put the video object here, ".title".
We need to make the same change in MessageService.
Now a quick way to find that class instead of going into
tabs or in the Solution Explorer is
just with Resharper type control t. And then type of MessageService.
There we go. We are in that class now.
So I'm going to go here and change this to
VideoEvenArgs and when outputting the message I'm also going to add args.Video.Title.
That's it.
Let's compile and run the application with control and F5.
Okay, note that here when MailService was notified,
now we got the title of the video.
So this is a way to pass data about the events that happened.
Okay, the next step is to show
we a simpler way to achieve the same thing with writing less code.
So let's go to our video encoder which is the publisher.
See, we created this delegate here and
specified these parameters as the arguments of the event handler method.
Now what they have done in.NET,
I think it came with.NET Framework Version 2.0 or 3.0,
to make our life easier, they said, okay,
we don't have to go and create a new delegate every time we want to declare an event.
So in.NET they have a delegate type which is
called EventHandler and it comes in two forms.
One is just a normal form and one is a generic form which looks like this.
What this means is they have done the hard work.
So we can use that delegate instead of creating our own,
which means in this case when we are declaring
that event instead of creating a custom delegate like that,
we can just use the EventHandler delegate.
Note the icon here. I think it's a suitcase,
looks like they're... we are delegating it to,
I don't know, what it is called an English, solicitor, lawyer.
I don't know. So that event handler type is generic as we see here.
Now what do we want to send as additional data with the event?
VideoEventArgs.
Now that basically is exactly equivalent to this.
So we don't have to create a delegate explicitly.
We can just use this class here which is a delegate.
So I get rid of this.
Now if we want to publish an event without sending
any additional data instead of using a generic form like this,
we could just use the normal form, like this.
VideoEncoded, now this is complaining because of the duplicate name,
let's just use VideoEncoding.
In that case, that means a method that gets object source as the first parameter,
and EventArgs as the second parameter.
We don't really need it here.
Okay, with that change,
let's compile the application and run it.
Everything working as before.
Well I hope at this point we have a good and in-depth understanding of
events and delegates and how they help building loosely coupled applications.
We saw how we can use events to make our applications extensible and we
also saw how to create
a delegate and an event as well as raising and subscribing to events.
We also saw how we can use the event handler delegates that
comes in the.NET Framework which saves us from creating our own delegate.
So that delegate keyword that we saw earlier,
I just wrote it because I wanted we to know what's exactly happening behind the scene.
That came in the first version of.NET.
But then this event handler class came,
or delegate came and we don't really need to create our own delegates.
I honestly, I haven't seen a used case for that over
the past 12 years of me coding in.Net.
Okay, that's it for this video.
I hope we enjoyed this.
And thank we for watching.

Okay, extension methods.


What are extension methods?
Extension methods provide us the ability to add methods to
an existing class without changing
its source code or creating a new type that inherits from that.
Let me show we an example here.
Think of the String class.
Let's say we have a string variable called post
which supposedly should contain a long blog post.
This is supposed to be a very long blog post.
Blah blah blah.
Now we have seen that in blogs,
when we're looking at the index of the blog,
we see a summary or shortened version of the blog post.
So, there are a number of words and then there is... at the end.
We may want to implement something like that, shorten wer strings.
Well unfortunately, we cannot change
the string class because we don't have the source code,
and we cannot inherit from string.
Let me show we.
So if I create a class here.
All public, say, public class RichString that derives from String.
See, we get an error here: "Cannot inherit from sealed class 'string'.
So in situations like that,
we can use extension methods to add new methods to an existing class.
So, let me show we how we can
create a method on the string that will look something like this.
So I'm gonna call it Shorten which gets a number of words,
and then that would return, let's say,
a shortened version of the post.
To create an extension method,
we need to create a static class – that's the convention that we need to follow.
So we create a public class, public static class.
A good naming convention is to start with the class we're extending,
in this case, a String,
and then add the postfix Extensions.
Now here we can write wer extension methods.
And we should start with public and static always.
Now in this case, we want our shortened method to return a string.
And here is the name of the method.
The first argument of this method should always be
this and the type we're extending and give it a name.
So that's a convention we need to follow.
And, in this case,
we want our shortened method to take a parameter of type integer called numberOfWords.
So with that method, as we see,
now that shortened method is absolutely fine.
I didn't have to inherit from the String class or change the String class' source code.
Now let's go ahead and complete this here.
But before doing so, I'm gonna put this class in a separate file,
so I would ReSharper,
alt and enter. Whoops. Not happy.
I'm using a Mac keyboard here.
Alt and enter, move to a new file.
So if the number of words is zero,
it would return an empty string.
Otherwise, we need to break up our string by the space character.
So I would say is str.Split,
space character here, and that would give me all the words in this string.
Now if there are less words than the number of words we have requested here,
we just return the original string.
But if there are more words,
we need to get only the first few words based on the number of words here.
So what we can do is we use the Take method.
Look, Take here is an extension method.
So, if we look at words,
the type of that is a String array.
String array, which is an array,
does not have a method called Take.
Later, Microsoft created an extension method called Take that can be applied
on any class that implements IEnumerable interface – in this case, the String array.
So we use Take method here,
and I take this numberOfWords,
and I will join them with the space character and just return that.
Now to make my code a little bit more robust,
if the consumer of this method sends a negative value as the numberOfWords,
that doesn't make sense,
so I'm gonna do some defensive programming here.
Say, if numberOfWords is less than zero,
throw new InvalidArgument – doesn't, InvalidArgument, no?
Throw new ArgumentOutOfRangeException, there we go.
And we give it a message,
"numberOfWords should be greater than or equal to 0.
Maybe even zero shouldn't be a valid choice.
Anyway, so let's review.
We created a static class.
We named it based on the class we're extending and then postfix Extensions.
All of our extension methods will end up here.
In this case, we have only one extension method.
They have to be public static,
and their first argument should be this,
the class we are extending,
and give it a name.
Now let's get back to our program.
Now because we are using that method on an instance of a string,
when we go to the extension method,
its first argument represents that actual instance that we are applying this method on.
So, let's verify that our code is working.
So Console.WriteLine(shortenedPost).
Let's run the application. There we go.
We only got five words: "This is supposed to be".
And we could actually make this method a little bit nicer and
say – to indicate that there are more words, "..." goes here.
Let's run the application.
"This is supposed to be... " So this is a good way of shortening strings.
Now, a few things we need to cover here
is – look at this namespace here: ExtensionMethods.
This is the parent namespace for my application.
So, both this class and my Program class are defined in ExtensionMethods namespace.
But if I go and change this namespace here to something like Extensions,
what happens is if I go back to Program,
that method is not recognized.
So, that's a key thing we need to know about extension methods: they come to
existence when the class that created them is in the scope.
So, in this case, I'm using ReSharper,
and ReSharper automatically detected that,
that Shorten method is defined in that class StringExtensions,
which is in Extensions namespace of ExtensionMethods namespace.
So I can add that,
we'll alt and enter.
The thing I don't like about this approach is
if we are using a few extension methods here and there,
we will end up getting a lot of namespaces like that on the top.
So, what I personally do is because the String class is
defined in the System namespace and I'm extending that here,
I would rather to use System here.
This way, whenever I'm defining a string,
I automatically have to import
a System namespace which gets that extension method as well.
Another thing we need to know about extension methods is
that even though we are applying them here,
on an instance of an object,
they're essentially static methods.
So, as we can see here,
there are static methods.
But with this convention that we follow,
we mark the class as a static and the method as static and this argument here.
C# compiler allows us to use that method on an instance object.
The difference is, if we use.,
note that – where is that?.Shorten has a different icon from the normal methods,
the normal instance methods defined in the String class.
And that's the icon of the extension method.
The other methods have this kind of purple cube.
Shorten. So the lesson is,
these static methods can be troublesome at times.
The problem is, let's say we extend the String class,
but the creator of the String class,
in this case, Microsoft,
ends up changing the class' implementation and they may create
a Shorten method with
exactly the same signature but it may behave differently from wer code.
What happens is that,
the instance methods get priority over a static methods,
so wer code will never be executed.
So what Microsoft suggests in their guidelines is
use extension methods only when we really have to.
If we have the source code of the original class,
go ahead and change it there.
Otherwise, create a new type that derives from that class and add wer new method there.
And if that doesn't work,
then go ahead and use extension method.
In practical terms in the real world,
most often we will be using extension methods instead of creating them.
A very good example of that is IEnumerable interface here.
Let me create an instance of IEnumerable of integers.
Let's call it numbers,
and let's assign it to a list of integers.
So list is a generic,
so is the IEnumerable interface.
Now if I type numbers., look,
these are the methods that are defined in the IEnumerable,
like Get Enumerator; but look,
these are the extension methods.
And here I'm using ReSharper,
and ReSharper is great because it's telling me that
this extension method is defined in this namespace, Linq.
So these are the extension methods that come with Linq which allow us to query objects.
So as we see, there are quite a bunch of them here.
Very, very useful.
I'll cover them in a future video.
So, if I want to use,
let's say, the Max method here,
ReSharper automatically added a reference to that namespace,
so that extension method is now valid.
Now Max method, what it does is it looks at that list and returns the biggest number.
So let's initialize that list.
Here, I'm using the object initializer syntax.
I can put numbers here immediately: 1, 5,
2 – sorry – 3, 10, 2, 18.
I can use the Max method and that returns the – whoops – that returns the largest number.
And I can put that on the console.
Let's run the application. So 18 is the biggest number.
So, as we see, these extension methods are very useful and
most often we'll be using them as opposed to creating them.
That's it for this video. I hope we enjoyed it,
and thank we for watching.

So, we go to LINQ.
What is this LINQ that everybody talks about?
LINQ is one of my absolute features of C#.
It stands for Language Integrated Query and it
gives the capability to query objects in C# natively.
So with LINQ, we can query objects in memory like.NET collections,
we can query databases,
we can query XML and we can query ADO.NET data sets.
Querying.NET collections or objects in the memory is
often referred to as LINQ to Objects.
Querying databases is often referred to as LINQ to Entities.
Querying XML is often referred to as LINQ to XML and
querying ADO.NET data sets is referred to as LINQ to Data sets.
Now this is a comprehensive topic and is beyond the scope of this video.
Especially LINQ to Entities, which is,
use in Entity Framework is a big topic,
and it needs its own course.
I'm actually planning on releasing a good comprehensive course on Entity Framework.
So, if we're interested,
make sure to stay tuned.
Now, in this video I'm going to show we the basics of LINQ,
and get we started.
I'm going to cover a lot of ground,
so we have a good understanding of LINQ,
and what problems it resolves.
So, let's jump into code.
Here in this project, I've got a simple book class with two properties,
string Title and float Price.
I also have this BookRepository,
which has one method called GetBooks,
which returns an IENumerable of Book.
Basically, I have a hard-coded,
a few book objects here in the list.
So here, I'm returning a new list.
This is a generic list of books.
I'm using the object initializer syntax here,
to immediately initialize this list.
And then here, I'm adding a new book, again,
using the object initializer syntax,
to immediately initialize a book.
So as we see our books here have-- Title and a Price.
Let's look at our Program.cs in the main method.
We simply instantiate the BookRepository called the GetBooks method and get the results.
Now, let's see what we can do with LINQ.
Let's say, we want to display the list of books that are cheaper than $10.
If we didn't have LINQ,
this is what we had to do.
We would have to create a new list.
We would have to iterate the books collection and then say,
if book.Prize is less than $10 added to CheapBooks collection and finally,
at this point we have the list of CheapBooks.
So here we could iterate this collection
and display each book title plus its price.
So let's run this code.
So these are the books that are cheaper than $10.
Now, with LINQ, we can get rid of
this piece of code here and do it with one line of code.
So how?
All we have to do is to say "var CheapBooks = books.".
Take a look at these methods here.
These are extension methods and we should be familiar with extension methods.
So if we skipped that video,
make sure to watch it first and here we see that
these extension methods are defined in the namespace here, LINQ.
So let me show we a method here,
where, we use where to filter collections.
Here I'm using ReSharper and as soon as I use the Where method here,
ReSharper immediately added a reference to system that link for me.
If we're not using ReSharper,
we have to manually add the reference here.
Now let's take a close look at the Where method.
The Where method takes a Func of Book and bool.
Remember Func, it's a delegate.
It points to a method that gets a book as an argument and returns a boolean value,
and this is what we call a predicate.
So the general predicate is to get a book,
assess some condition and if the condition is
true returns that book such that it will be added to the output.
So, whatever we see Func as a delegate,
we can use a lambda expression.
Remember lambda expression?
If we'll skip that video, make sure to watch it.
So a lambda expression is a way to write
an anonymous method and that can be assigned to a delegate like Func here.
So here, I will write to lambda expression.
Like b goes to b.Price is less than $10 (b => b.Price <10).
So just to refresh wer memory,
on the left side of the lambda operator we have
argument and on the right side we have the actual expression.
So this is like an anonymous method, that gets b,
which is a book as an argument and executes this condition here.
But it's more accurate to say evaluates this condition.
So if the condition is true,
that book will be added to the list of filtered books,
which will be CheapBooks.
So with this line of code, we can easily get the list of books that are less than $10.
That's from the application.
There we go, we got the same list of books.
Now, let me show we another method here.
LINQ also has a method called OrderBy and OrderByDescending,
and this is used for sorting collections.
This method gets an argument of type,
Func of Book and TKey (Func , which is generic.
So again, this is a delegate that takes a book and then here we need
to specify the property of the book on which we would like to sort the collection.
So, I can write a lambda expression here saying b.Title,
assort them by Title.
Now what we can do here,
which is extremely powerful is we can chain these LINQ methods.
So here, I can put OrderBy right after Where.
In this case, I am filtering the list of books here and then ordering them by Title.
Let's run the application again.
Note that the list is now sorted by Title.
LINQ also has another powerful method and it's called select,
and select is used for projections or transformations.
Let's say, we want to iterate the list of books
and for each book we will like to convert it to
another object or maybe we would just like to select one of its properties as a string.
Let's say, we get a book and select its Title.
So here, if we call this method,
the result here if we hover over var.
Look, the result is an IEnumberable of T and T is a string.
So with Select here,
we are converting a list of books which have been previously filtered and sorted.
We are converting that to the list of
strings because we are only selecting the Title of the book.
So now that we iterate this CheapBooks collection,
we don't have this Title and Price properties anymore because book is now a string.
So let me comment this out, Console WriteLine book.
Let's run the application.
So we just got the Title of the books.
Now in building real world applications sometimes
the lambda expressions we write here get a little bit complex.
So there is a common convention to lay out
wer LINQ method here and that is to lay them out like this.
This way it's more readable and cleaner.
So we filter, we sort, and select the property.
Now this syntax is what we call LINQ Extension Methods.
We also have another syntax to write LINQ queries and that's what we
call LINQ Query Operators (Query Operators).
I'm going to write the exact same code,
but using a LINQ Query Operator.
So I'm going to call this one CheaperBooks.
This is how we write it, from b in books,
where b that price is less than 10, order by b.
Title and select b.Title.
So these two are exactly equivalent.
LINQ Query Operators always start with the From and always finish with the Select.
So here from we are saying from b,
that's like an argument in books.
Now we filter by b.Price,
we order them by b.Title and then finally,
we select b.Title or we could just return the actual book object.
In this case, we will get a list of books.
If I hover my mouse here.
We see, we get an IOrderedEnumerable of TElements and TElement is Linq.Book.
Which syntax we use is I would say purely personal choice.
In terms of power and flexibility this syntax is more powerful
because internally all these keywords translate to this extension methods here.
And we'll find that in more complex scenarios.
There are not keywords for every extension methods that we have here.
But also in other scenarios like when we are doing it GroupBy or Grouping lists.
I think this syntax is more friendly and cleaner.
So there is no right or wrong.
It really depends on the situation and on wer personal choice.
Now for the rest of this video,
I'm going to just stick to LINQ Extension Methods and show we
some really cool extension methods that make wer life much easier.
So I'm going to get rid of this stuff here,
actually I will delete this here as well.
We'll look at more examples in a second.
So let's take a look at our list here.
Here we have a book called ASP.NET MVC.
Let's say, we want to return only that book.
Where method we have seen so far returns a list of books and IEnumerable,
but if we want only a single object in the result,
that's when we use the Single method.
So Single as pretty much the same argument as the Where.
It gets a function of Book and bool,
which is a delegate and we can use the lambda expression here.
So I would say give me the book whose Title is ASP.NET
MVC and I call it here book.
Let's put that on the console, book.Title.
Let's run this. So here is our book.
Now let's see what happens if I add something here,
but obviously we don't have a book by that name.
When I run this, the application crashed.
We got an unhandled exception,
Invalid operation exception, Sequence contains no matching element.
This is one of the errors that we see a lot when working with LINQ.
So, Single method expects that there must be
one and only one object in wer collection that satisfies this condition.
Now, if we're not sure if that object exist or not,
we can use SingleOrDefault.
The difference is, if there are no objects matching this condition,
Default will be returned,
which in this case would be null.
So, ny book object here will be null and I cannot access the Title property.
Let me just show we that book is null,
is true. Let's run this.
There we go-- the book is null.
We also have a few other similar methods to Single,
one of them is First.
Now first is used to get the first object in a collection.
Optionally, we can supply a predicate, the filter.
Say give me the first book whos title is... let's
say C# advanced topics.
Let's take a look at our BookRepository here.
So we have two books called C# advanced topics,
and I want to get the first one.
So, I use the first method here and here let me uncomment this,
and also at the price of the book.
Now let's run the application.
So we got the book that is called C# advanced topics and it's $7.
Let's look at our BookRepository.
See we have two books here and the first one is $7.
Similarly, we also have a FirstOrDefault and this is similar to SingleOrDefault.
So if there are no books that match this condition.
This method returns NULL instead of throwing an exception.
We also have a method called Last or LastOrDefault,
and we should guess what they do. So let's try this one.
Let's run this. So in this case,
I got the book-- that is $9.
And other useful link extension method is...
Skip and Take.
What are these?
These are used for paging data.
So with Skip we're saying,
skip two records or two objects and take three.
Let's see if it actually works,
because here I've got one,
two, three, four, five.
That's fine. So, It's going to skip the first two and return the next three.
So let's run the application.
Now this method returns an IEnumerable of book.
So this should be books.. and I would..
Whoops sorry the name is conflicting with this books here.
So I'm going to call this pagedBooks.
And I would iterate the collection,
pagedBooks and put that pagedBook Title on the screen.
Let's run this. So we got the ASP.NET Web API,
as well as C# Advance Topics.
Let's double check.
So, we skipped two objects here and we got three objects.
So Skip and Take are pretty useful.
We also have a bunch of aggregate functions like we have in SQL.
For example, let's say we would like to count the number of books,
and of course this is not going to be pagedbooks,
it's going to be count.
And let's just put that on the console,
but we have totally five books.
We also have a useful method here called Max.
Which is used to return an object that as assumed max of something in a collection.
So in the list of books, what does Max mean?
We kind have to give it a meaning.
In this case, they can look at them.
Arguments, we can pass a delegate that takes a book and returns some value here.
Bu what I can do is,
say return a book that has the highest price.
Let's run the application.
That's $12. Well, count is not a good name.
At Max method, is returning actually the price,
the highest price, not the book that has the highest price.
So that would, that should be called Maximum price.
Similarly, we can have minimum price.
Tell me how much is the cheapest Book.
Sorry, I forgot to put that on the console.
So this one is going to be minimum price.
So a minimum price is $5.
So Max, Min, Count and we also have Sum.
Let's say we would like to sum this collection based on the price of books,
and we call this perhaps,
TotalPrices which actually doesn't make
sense in this case but I'm showing we as an example.
So, the sum is $42 and 99¢.
So what I wanted we to learn in this video were these extension methods here.
Books.Where to filter and return a list of books that match a given condition.
Or we can use Single to return only a single book that matches a given condition.
Or SingleOrDefault which is safer to use because single,
if it cannot find any books that matches the given condition it throws an exception.
Whereas, SingleOrDefault returns none.
So these are for filtering.
We also have the First,
as well as FirstOrDefault which is safer.
We also have Last,
as well as LastOrDefault.
We also have a bunch of aggregate functions, like Min,
like Max, like Count, like Sum.
I think we even have an Average, there we go.
So we can pass a delegate,
say give me the average of the price.
We also have useful methods here.
Skip and Take, which is used for paging.
Now, the beauty of LINQ is whether we're quering objects
into memory or we're quering XML or we're quering database,
we keep using LINQ like this.
We don't have to learn Xquery to query XML,
or we don't have to learn Transact-SQL to create databases.
Well, it's good to know SQL or programming databases, but in general,
we can use LINQ in a lot of cases and what LINQ does for we or what Entity Framework
does more precisely is it takes this LINQ extension methods and when we call them,
it translates them to SQL query.
So we never have to go and create a story procedure.
Again, this is a very comprehensive topic and it's beyond the scope of this video.
Hopefully, I will release my Entity Framework Course soon,
and there, I will explain all of these amazing things that we can do with LINQ.
I hope this video gives we a good foundation to start with LINQ.
See what benefits we get and as we prepare for real world applications.
I hope we enjoyed it and thank we for watching.

Okay, nullable types.


What are they and why do we need them?
In C#, as we probably know,
a value type cannot have null.
So if we define a bool,
it can have either a true or a false.
But there are situations that we would also like to cater for null values.
For example, if we're working with a database and we have a table
called Customers which has a column called Birthdate.
Birthdate can be nullable because not everyone wants to put in their birthdate.
In that case, if we want to map that table to a C# class,
that's one of the cases where we use a nullable type.
Let's see how nullable types work in action.
So I define a DateTime here,
call it date, and set it to null.
See, we immediately got an error.
Why? Because DateTime is a value type and,
as a result, cannot be set to null.
We can solve that issue by using Nullable.
Nullable is a generic structure that is defined in the System namespace.
So with that, now we can have a variable that can have either null or a valid DateTime.
We can rewrite this code and make it a little bit shorter.
The shorthand of defining nullables is to type
the value type and then append a question mark.
Now let's take a closer look at the members of a nullable type.
Here are the properties and methods of the nullable type: GetValueOrDefault,
HasValue and Value are the three members that we'll be using all the time.
Let me show we the difference.
It's best to show them by an example.
So I'm going to put them on the console,
date.GetValueOrDefault,
date.HasValue and date.Value.
Actually, I would like to add a label here,
so "GetValueOrDefault(): " +.
And here, I output "HasValue: ",
so it's clearer what value each line is representing.
Oops. And here that would be "Value: ".
Let's run the application and see what happens.
We got an exception; the application crashed.
Let's take a closer look.
So here, GetValueOrDefault returns a value if the object has been initialized
with an actual value or returns the default value for that data type if it's not.
In this case, because we set our data to null,
it's trying to return the default value or a
DateTime which is day one of months one of year one.
If we define a nullable bool,
this method would return false if we forget to initialize it.
HasValue returns true if the object has a value,
but if it's null, it returns false.
In this case, because it's null, it's returning false.
But look at the last one here.
When we access the Value property,
we got an exception,
and that exception is of type InvalidOperationException.
It's saying nullable object must have a value.
So basically the lesson here is,
when we access the Value property,
we should make sure that wer object has a value.
Otherwise, we're gonna get an exception.
That's why we have this method here.
So this is the preferred way of getting the value.
This way, if the object has a value,
we will get it; otherwise,
we'll get the default value for that value type instead of getting an exception.
Now let me show we something else about nullables.
First, I clean up here,
and I actually set the date value here.
So new DateTime, let's say 2014, first of January.
I define another DateTime.
Let's call it date2 and set this one here.
See, we immediately got an error.
Why? Because we're trying to put a nullable DateTime into a DateTime,
and the compiler doesn't know how to respond to that. What if it's null?
What should we do? Compiler doesn't know.
So in situations like that,
if we get that error,
what we need to do is access that GetValueOrDefault method.
In that case, because we have a value here,
that will go straight into this date2. Let's verify that.
There we go. All good.
Now let's take a look at the other scenario.
This time, I define a nullable DateTime and try to put date2 here.
So in this case, we don't need to call this method or do any casting.
A value type can easily be converted to a nullable type, as we see here.
So let's display date3.GetValueOrDefault. There we go.
Now let me introduce
we to an operator that is pretty useful when writing code.
It's called null coalescing operator.
So basically, let me clean this up here,
and maybe just set this to null.
Let's say we would like to write a code like this.
If date is not null,
set date2 to date.
Otherwise – sorry, this has to be
date.GetValueOrDefault because of the reason I just explained.
Otherwise, if date is null,
we would like to give date2 some default date, let's say, DateTime.Today.
So in that case, because my date here is null,
this else will be executed in which case we set today's date here.
Let's verify that. date2. So today is 20th of November, 2014.
Okay, let's get rid of that.
Now we can rewrite this block here much shorter.
Let me show we how it works.
So here I say date, null coalescing operator,
which is double question mark, and then DateTime.Today.
Basically, how we read that is if date has a value,
put it here; otherwise, use this value.
It's a little bit similar to the tertiary operator.
Let me show we. We should have probably seen this.
DateTime date3 is if date is not null,
use date; otherwise, use DateTime.Today.
Sorry, that should be.GetValueOrDefault because we are
converting from a nullable DateTime to a DateTime.
So, this is the tertiary operator in case we haven't seen that before.
So this is the condition, that's the if.
If that is true,
this will be executed until this colon.
Otherwise, this will be executed.
Now, null coalescing operator is even a shorter way of writing this code.
So we put wer variable on the left side.
If it has a value, it goes here.
Otherwise, if it's null, we use this value.
Well, that's pretty much it about nullable types.
I hope we enjoyed this video, and thank we for watching.

Okay, Dynamics.
Dynamics is one of the features of C# that sometimes confuses some developers,
but it's actually pretty easy.
Let me give we some background information.
Programming languages are divided into two types —
statically-typed languages and dynamically-typed languages.
Or in short, we can say static languages or dynamic languages.
Examples of static languages are C# and Java.
Dynamic languages are like Ruby,
Javascript, Python, and so on.
But what's the difference?
The difference is in static languages — resolution of types,
members, properties, methods is done at compile-time.
So if we try to access a method that is not defined in an object,
when we compile the application,
we are getting an immediate feedback that's telling us
that method or property is not found on that object.
With dynamic languages — the resolution of types,
properties, members, methods is done at run-time.
But what's the benefit of that?
First, I'm not an expert in programming languages,
but based on my understanding,
dynamic languages are a little bit easier and faster to write code with.
But on the flip side,
because we lose compile-time checking,
we have to write more unit tests to make
sure the application behaves properly at run-time.
Now, C# started as a static language,
but in.NET Framework version four,
they added dynamic capability to it,
and the intention was to improve interoperability with
COM or dynamic languages in.NET like IronPython.
If we're writing code for Microsoft Office applications such as Word or Excel,
dynamic is a feature that is going to help we a lot.
Without dynamics, we have to use reflection.
What is reflection?
Reflection is a way to inspect the metadata about the type,
and access properties and methods.
Let me show we an example.
Let's say, I have an object here.
Give it a name of "obj" and assign it to a string, my name.
I can call the GetHashCode method here,
like this, and that's pretty easy.
But with reflection, if I want to call that method,
my code will end up looking like this.
First, I get the type of that object.
And then, I get a reference to a method,
called GetHashCode, and that returns a methodInfo object.
Now, I can invoke methodInfo,
like this and pass some weird arguments here.
As we see it, this code is not very beautiful.
So reflection is a little bit difficult and messy.
The benefit of dynamic is that,
let's say, we're getting an Excel object,
and we know that that object should have some method called, I don't know,
let's call it — let's define an object here, excelObject.
I set it to a string for now,
just for simplicity because I really don't have Excel objects here.
And let's say, we know, I'd run-time that object,
should have a method called, Optimize, for example.
We see that we get compile-time error,
because the object class here does not have a method called Optimize.
With dynamic, we can easily resolve this problem without having to use reflection.
With reflection, our code would end up like this,
whereas with dynamic, it looks like this — it's much cleaner.
So that's how we use dynamics in C#.
But how does all the magic happen,
as in resolving types,
properties, members at run-time?
We should be familiar with CLR or Common Language Runtime.
It's.NET's virtual machine that gets
wer compiled code which is in intermediate language, which is I_L.
Then, converts that or recompose that into machine code at runtime.
In.NET Framework version four,
they added a new component called DLR,
which is a Dynamic Language Runtime.
So DLR sits on top of CLR,
and gives dynamic language capabilities to C#.
Now, most often we are not going to work with that, it's just there.
I'm just telling we that this is how the magic happens.
Now, let's take a look at a few other things about dynamics.
I can define a dynamic, type here,
give it a name here,
and assign it to my name.
And then, the next line,
I can assign an integer to it.
And that's perfectly fine.
With static types, like object, int, string,
or whatever, this is not possible — we're going to get an exception.
But if I run this code,
the application runs successfully.
There are no exceptions.
Let's inspect this, I put a breakpoint here with F9.
Run the application in debug mode with F5.
Continue execution with F10.
Let's put a watch on the name variable.
Take a look here.
So name is a dynamic,
and it's runtime type is a string.
But if I continue execution with F10,
now its runtime type changes to integer.
And that's one of the key differences between dynamic types and static types.
With dynamic types, we can do whatever we want with them.
And I think that's what makes them powerful in terms of writing code faster and easier.
Now, let me show we another example here.
If I remove this line and instead try to apply a '++' operator to this name variable.
Let's see what happens. This time we got an exception.
Unhandled exception, its subtype, runtime,
binder exception which is a popular exception when working with dynamic types.
And the exception message says,
operator '++' cannot be applied to operand of type 'string'.
So, at runtime, let me cancel that.
So at runtime, the type of this name variable would be string.
And of course, we cannot do that with a string,
and that's the reason I told we — with dynamic types,
we need to write more unit tests to make sure application behaves properly at runtime.
Let's take a look at another example.
I'm defining a dynamic called "a",
set it to 10.
And "b", set to 10,
or let's say five.
This time, I'm going to define a variable with var.
Now, var is not dynamic,
var is basically a shorthand way of writing
code and letting the computer decide what type a given variable should be.
So if I say, var c equals string, empty string,
and I hover my mouse over var,
then var is a string.
It's a short way of writing code.
I could just write string here,
but var is a little bit shorter.
Now, the interesting thing here is if I define "c" as "a plus b",
because a and b are dynamic,
c will end up being dynamic.
Look, that's dynamic.
Let's put a breakpoint here.
Run the application in debug mode.
I'm going to do this watch here,
and put a, b, c here.
So, continue execution with F10.
So a is dynamic,
and this runtime type is integer — so is b,
and so is c. So when we use dynamic variables in an expression,
the expression will end up being dynamic as well.
One more thing we need to know about dynamics is conversions or casts.
Most often, with dynamics,
we get implicit conversion from and to the target type.
So let me show we an example here.
So I define an integer called "i" and set it to five.
Now I can define a dynamic called "d" and set it to "i".
In this case, I didn't have to specify a type cast or conversion.
At runtime, d will end up being an integer. Let's verify that.
So continue execution with F10.
They put d here, in the watch window.
So "d" is a dynamic and it's runtime type is integer.
Similarly, we can put dynamic on the right side of
the assignment operator without the need to do any explicit casting.
So if I define a long "l" here,
I can put d inside long.
At runtime, d will be an integer, and of course,
we can't put an integer in a long variable without explicit casting.
So the lesson is — when converting from dynamic to static types,
if the runtime type of the dynamic object is implicitly convertible to the target type,
we don't need to cast it.
So let's verify this.
So F10, F10, and I put a "l" here,
and "l" as we see it's long and its value is five.
And "d" is, of course, dynamic and its runtime type is integer.
Well, that's it for this video.
I hope we enjoyed it, and thank we for watching.

Okay, exception handling. In C#,


we can use exception handling to deal with
unexpected or exceptional situations that arise when a program is running.
As.NET Developers, we need to learn how to handle exceptions effectively.
Let's get started with the code.
Here we have a calculator class with
a simple method called Divide which gets two arguments,
a numerator and denominator.
For simplicity, I have left out the other methods.
In the Program.cs, we simply instantiate that calculator and then call the Divide method.
We are sending zero as the denominator.
Let's run the application.
The application crashed, and this is something that we need to avoid.
Let me cancel this here.
Take a look at the console here.
It says Unhandled Exception,
and that exception is of type System.DivideByZeroException.
DivideByZeroException is a class that resides in System namespace.
So in.NET, an exception is essentially a class.
And here is the message about that exception,
Attempted to divide by zero.
And the rest is what we call a stack trace.
A stack trace shows the sequence of
methods that were called until the exception was thrown.
In this case, we got the exception at
this divide method which is defined in
the calculator class in the exception handling namespace.
And that happened in line seven.
And before we called that method,
we were here in program main method in line nine.
So this is the stack trace which shows a sequence of
method calls in the reverse order. Let's close that.
Now to handle exceptions,
we use try catch blocks, something like this.
So we put the code that may throw an exception inside the try block.
When an exception happens,
the catch block is executed.
If there are no exceptions,
this piece of code will not be executed.
So in this case, let me move these two lines here and the try.
In the catch block, we usually have two choices.
We can recover from the error and prevent the application from crashing or we can,
what we call, rethrow the error that
means send the error back to the caller of this code.
In this case because the main method is the starting point of the application,
it doesn't make sense to rethrow the error.
So what we're going to do here is just to display a user friendly message to the user.
Now if I run the application again.
See, this time the application didn't crash.
We just got an error here. And this is better.
It's not ideal but it's better than an application that crashes.
So as a guideline,
we should always have a global exception handling block in wer application.
Now here we are using a console application
and each console application has a main method.
That is the starting point of the application.
And here is where we have our global exception handling block.
If we are creating an ace dotted application,
we don't have a main method there.
And there is a different way to implement something like that.
I believe in Windows Presentation Foundation or
WPF applications we should have a similar main method.
Obviously I don't remember because I haven't done it for years.
Now let's take a closer look at exceptions.
Here in the catch block we just have a type.
And that exception is the parent of all exceptions in.NET.
It's good to have an argument here so we can access the actual exception.
Now I'm going to put a break point here using F9,
and run the application in the debug mode with F5.
Let's take a look at the ex argument here.
Take a look at these properties here.
Message is the error that is associated with the exception.
Source is the name of the application that generated the error.
Sometimes wer application might have multiple assemblies or DLLs.
So more accurately, source represents
the DLL or the assembly that this exception happened in.
Stack trace is what I told we earlier,
it's the sequence of method calls in the reverse order.
So if I click this magnifier icon here, let's take a look.
So the exception happened at this line,
line seven of Calculator.cs file,
which was actually the divide method in the calculator class.
And before we got to this method we were here.
Now this is a very simple application.
In real world applications,
we often see the stack trace includes quite a few number
of method calls. Now let's close that.
Target site is the method where the exception happened.
So these four properties are really common when working with exceptions.
Inner exception represents an exception that could be inside this exception.
I will talk about that a little bit later in this video.
HResult, to be honest,
I have no idea what it means.
I believe it comes from the world of
Windows programming and it probably has a handle to the exception.
I really don't know. HelpLink sometimes comes with
some exceptions and obviously that's a link where we can find more about the exception.
In this case, nothing. It's null.
And Data, sometimes exceptions can carry more details with
themselves which is stored in data. Let's stop the debugger.
When handling exceptions, we can have
multiple catch blocks and they have to be from most specific to most generic one.
What do I mean by most specific or most generic?
Well, if we remember,
the actual exception that happened here was a DivideByZeroException.
Let's take a look at DivideByZeroException class.
So I type in DivideByZeroException here and then press F12 to go to Object Browser.
Look, here we have got DivideByZeroException and on this side,
take a look, it derives from System.ArithmeticException. So this is the parent.
If I click this, it shows me that that class derives from SystemException.
And if I click this, it shows me that SystemException derives from System.Exception.
So here we have a hierarchy of four levels of exceptions.
Exception class is the parent of all of them which is
the most generic one and DivideByZeroException is the most specific one.
So back here, let's say if our divide method could throw
different kinds of exceptions and we wanted to handle each differently,
we could have multiple catch exceptions here.
So we start with the most specific,
DivideByZeroException and more generic one,
which would be ArithmeticException and the most generic one which is the exception one.
Why do they have to be from most specific to most generic?
Because in C# or any object-oriented languages we should know
that this parent class can hold a pointer to any of his children,
which means if we put this at the beginning here,
any exception that happens,
that catch block would immediately get that.
So we won't have a chance to handle specific exceptions like this one here.
And as we see a C# compiler is intelligent enough and is complaining
about the order of catch blocks here and that's why we get this red underline here.
So I've put this catch block back to where it was.
Let's go ahead and write a different message here, so Console.WriteLine.
We cannot divide by zero.
Now if I run the application,
this is the message we get.
So this catch block was executed and it recovered from the exception.
So these two were not executed.
In C# we also have a finally block which looks like this.
Let me clean up some code here.
Let's get rid of these.
Okay, so why do we need finally block?
In.NET, we have classes that access unmanaged resources.
What do I mean by unmanaged resources,
that is resources that are not managed by CLR,
so there is no garbage collection applied to them.
Examples are file handles,
database connections, network connections,
graphic handles and in situations like that we need to manually do the cleanup.
Now any class that uses unmanaged resources is
expected to implement an interface called IDisposable.
Let me show we IDisposable here, IDisposable.
So we press F12 to jump to Object Browser.
Look, IDisposable is an interface and has a method called Dispose.
Which is where we do the cleanup.
And here is the summary specifies,
defines a method to release allocated resources.
So we use the finally block to call
the Dispose method of the class that uses unmanaged resources.
Let me show we an example.
So, I'm going to get rid of this calculator here.
Let's define a stream reader.
A stream reader is a class that is used for reading files.
So I can say,
Read a file located in C-Drive and it's called this file.zip.
In the try block, I can read the content of this file, say StreamReader.ReadToEnd,
and here in the finally block what we need to do
is call StreamReader.Dispose which comes from IDisposable.
So with this code if anything goes wrong inside the try block during reading the file,
we want to make sure that the stream would be closed.
This is extremely important because if we don't manage
these situations properly we will end up keeping files
open on the disk or keeping network connections open
or wer database connections and sometimes we get out of resources.
So make sure whenever we're using unmanaged resources that is files,
database and network connections,
graphic handles, make sure to dispose them here.
Now in terms of execution of this piece of code,
first this try block is executed.
If there are no exceptions,
this cache block will not be executed.
But the finally block will always be executed.
And if we happen to get an exception here,
we'll just write this message to the console.
And finally we'll close the StreamReader.
Let me show we that in the debugger.
So let's manually throw an exception here.
We can throw an exception using the throw keywork.
And let's call an exception.
Whoops. So I put a breakpoint here in F9.
And run the application.
In the debug mode,
with F5. Well, interesting scenario.
In fact, we got an exception right at the beginning here.
This file actually did not exist on my local C drive.
So in this case note that we didn't actually write a proper exception handling code.
So let's stop the debugger.
This means if I run this application,
it's going to blow up,
we got an unhandled exception and the application crashed.
So a better way was to actually write this here inside the try block,
so if the file is not found we make sure we catch the exception.
The only problem is because I defined StreamReader inside the try block,
I cannot access it in the finally block.
They have different scopes.
So what we need to do is go ahead and say StreamReader,
StreamReader, and then assign it here.
And of course, I have to initialize it to null here,
Otherwise I shouldn't call one of its methods.
And notice here, I'm getting a warning saying
possible null reference exception and that happens
if the StreamReader is not initialized properly here.
So a more reliable code is to say if StreamReader is not null then dispose it.
Now let's remove this breakpoint here.
So I press F9 again.
And put it here.
Now I run the application in debug mode with F5.
With F10 I continue execution,
so the control is here.
I continue execution with F10.
We display the message on the console
and note that the finally block always gets executed.
In this case StreamReader is null,
so it wasn't initialized and it won't be disposed.
That's it.
Now there is a cleaner way to write this code.
We have a key word in C# called Using.
So instead of declaring a variable outside the try block,
then initializing it here,
and finally checking if it's not null and disposing it.
We can use the Using statement.
Let me show we how it works.
So basically I come here,
Using var StreamReader equals news StreamReader.
I get rid of this one here.
And, I don't need this.
I need this, put that here.
And we don't need this finally block.
So basically, when we use a using statement,
internally the compiler will.
Create a finally block under the hood. Which will.
Call the Dispose method of StreamReader.
So we don't have to manually call that.
Now inside the Using,
we can read the content of the file,
and of course this is our global exception handler which would be
here no matter whether we're using a Using statement or not.
So let's run the application again.
Good. So the application didn't blow up.
So, the Using statement is the preferred way as opposed
to creating a finally block and calling the Dispose method.
So at this point we should have an understanding of how to handle exceptions.
We have seen the try block,
we have seen the catch block,
we have seen multiple occurrences of the catch blocks from the most
specific to most generic ones and we have also seen the finally block.
But how can we create and throw custom exceptions?
And in what scenarios do we need that?
Take a look at this WeTube.Api class I have implemented here.
Let's say we are creating a Web site and as part of that we need to
get the videos for a given user and display them on a web page.
So this WeTube.Api Class encapsulates all that logic.
It gives the user name of the given user and returns a list of videos.
So here the code would look something like this.
Here we have a try catch block,
inside the try block we access WeTube web service.
We probably may have to open a network stream, read the data,
like as an xml, and then parsing,
create a list of video objects and let's not worry about that low level complexity.
But what matters here is.
There could be quite a few number of reasons where
something could go wrong during fetching videos from WeTube.
And often they would be very low level exceptions like network stream.
I don't know, parsing exception, whatever.
We do not want to expose
these lower level exceptions to the higher layers of wer application.
So in situations like that.
We may want to create a custom exception
called WeTubeException and handle it differently.
For example when recovering from that exception,
instead maybe we want to display a list of default videos instead of WeTube videos.
So let's go ahead and create a custom WeTube exception.
First I created class, public class,
call it WeTubeException, and that should derive from a System.Exception.
Now with Resharper, I select this class.
I put the cursor here,
press alt and enter,
and enter again, and it moves into a separate file.
Typically here what we need to do is to create a constructor.
So I type in ctor,
that's a code snippet,
press tab and got the constructor.
And here we need to define two arguments,
StreamMessage, and exception, innerException.
So with this constructor then we can call
the base constructor of the exception class and
pass that message, and the innerException.
That's all we have to do.
Then, in WeTube. Api class,
let's say in the try block,
something could go wrong here.
It could be low level exceptions.
They can catch all of them here.
Maybe we would like to log them somewhere.
And finally, we would like to wrap them inside
a more meaningful exception like WeTubeException.
So here as a message I would say "Could not fetch the videos from WeTube."
So this exception is a lot more meaningful than say,
a low level socket exception or parsing exception in the xml.
And as a second argument I can pass
the actual exception which will be wrapped inside this WeTube exception.
Why do we do that?
Usually for troubleshooting.
So when we are troubleshooting the application we look at WeTubeException,
and then look at the innerException to see what is the actual problem that happened.
So as we see to throw an exception we use the key word throw.
And then new, and the type of exception.
Let's throw an exception here just to simulate how this would work.
Oops, some low level WeTube error.
So in the try block,
I manually throw an exception to simulate a real world scenario.
Then I will catch that here.
We don't have logging yet but I'm going to encapsulate
that actual exception here inside more meaningful exception.
Let's go to our program.
And in the try block,
let's create an instance of WeTube.Api,
and call the GetVideos method.
And that's my name here,
var Videos equal api.
Now what we can
do here is that exception would essentially be a WeTube exception,
so if I display the message for that, let's see what happens.
We run the application.
Could not fetch the videos from WeTube.
Let's run the debugger and see exactly what is happening.
So I'm going to go to WeTube.Api,
put a breakpoint here.
Run the application in debug mode.
Continue with F10.
So we throw an exception. And we catch it here.
This exception is of type exception, System.Exception.
And the message is, "Oops.
Some low level WeTube error."
Now here, we are throwing a new WeTube exception,
wrapping that low level exception before.
So as we come out of that we will get to
the main global exception handling block inside our main method.
If we look at that, x,
let's continue execution by F10.
Let's take a look. It says "Could not fetch the videos from WeTube."
Because this is our custom exception.
And if we look at the inner exception, it says, "Oops.
Some low level wetube error."
So, in the real world when we use
something like Entity Framework which is used for accessing database,
we're going to see that in wer exception all the time.
We get more generic exceptions.
And then we keep looking at the inner Exception to
find the actual reason something went wrong.
Well that's it for this video.
I hope we enjoyed it. And thank we for watching.

Okay. We go to Asynchronous Programming.


One of the things that confuses developers is
asynchronous versus synchronous execution model.
So, in this lecture, I'm going to explain the difference between
synchronous and asynchronous execution model.
And then explain how we can do asynchronous programming with C#.
In a synchronous program execution model,
program is executed line by line, one at a time.
When a function is called,
programming execution has to wait until
the function returns before it continues execution to the next line.
Let me show we a demonstration of that.
Imagine here we have a piece of code with four lines.
In the second line, we are making a call to
a function that is going to be a blocking operation.
It's going to be time consuming.
An example of that is when we access a database or website.
So, as we run this program,
we'll see that each line is going to be green,
and we will notice that in the second line there is going to be a delay.
Let's take a look.
So here is a delay.
So we notice that we blocked on the second line.
Now in a synchronous program execution,
when a function is called,
program execution continues to the next line
without waiting for that function to complete.
So let's do another simulation again.
This time we will notice that the second line executes
immediately and the control will go to line three and four.
In the second line,
we provide a callback to that time-consuming process function.
So when the execution of that function is finished,
then that callback function will be called.
Let's take a look.
So as we see, the program runs more smoothly.
We didn't block on the second line.
So what's the difference?
Asynchronous programming model improves responsiveness of wer application.
We have already seen that in the real world.
Think of Windows Media Player or wer web browser.
In the case of Windows Media Player,
as it's playing in media,
let's say a song or a movie the UI continues to be responsive,
we can resize the window,
we can move it around,
we can see an animation.
If Windows Media Player did not utilize asynchronous programming,
as it was accessing the file system and reading
a piece of music that we know would freeze,
we could not touch that window.
Same for wer web browser.
As a web browser downloads content from the Web,
the UI is still functioning,
it's responsive, and that's the benefit of asynchronous programming model.
So when do we use asynchronous programming?
Anytime we have a block in operation such as accessing the Web,
working with files and databases,
working with images and so on.
Now, how do we do that?
Well, traditionally in C# we had two common approaches.
One was using multithreading,
one was using callback methods.
Both these approaches are complex,
to learn and understand.
So, in.NET Version 4.5,
Microsoft introduced a new asynchronous programming model,
which is called Task-based Asynchronous Model.
And we achieved that by using async and await keywords.
And that's the topic of this lecture.
So let's jump into Visual Studio and learn about async and await.
Okay. Here I've got a basic WPF application with one form and a button here,
and behind this form we have a handler or clicking of that button.
First, let's see how asynchronous operation
can affect the responsiveness of our application.
So, I'm going to create a method here.
DownloadHtml, that takes a url.
We're going to use the WebClient.
And then, get the Html and that URL using DownloadString method here.
So, DownloadString takes a URL and returns a string which in this case is in Html.
Now, we need to write that Html to a file on the disk.
So let's use StreamWriter for writing that Html to disk.
And I'm going to store it
in a file here called result.html in my projects folder, it doesn't really matter.
And here we use streamWriter.write to write that html to this file.
Pretty simple, right?
Now, in the button click I'm going to call this method and
pass an address like msdn.microsoft.com.
Let's run this application.
So, when I click this button here,
it's going to take a couple of seconds until we download that Html.
And during that time,
this window is going to be unresponsive, which means,
if I try to drag and drop it,
it's not going to happen or we cannot even resize or minimize this window.
Let's see what happens. So, click.
Look, it's not moving.
Now it moved, because the Html was downloaded. Let's try again.
Click, I cannot move this up.
There was a tiny delay here.
So it depends on the operation.
The longer the operation,
the more unresponsive the UI is going to be.
Now, let's see how we can improve these by using an asynchronous operation.
So, I'm going to write an asynchronous version of this DownloadHtml method.
So, let me scroll down a little bit so we can see easier.
We start with public.
All the asynchronous methods should be decorated with the async keyword.
So, we put async here.
Now, for the return type we need to return a task object.
What is a Task?
A Task is an object that encapsulates the state of an asynchronous operation.
It comes in two forms.
One is the non-generic form,
which is this one here and one is generic form.
So, if wer method returns,
let's say a string,
we need to use the generic version of the Task.
So, that would be Task of string.
If wer method is void,
we need to use the non-generic version of Task which is just this one here.
So, we return Task here.
Now we name our method DownloadHtml and by convention we need to add the async
suffix.
We don't have to but this is the recommended practice from Microsoft.
And then, we're going to use the same parameter here.
Now, let's copy-paste this code inside our new method.
Well, at this point,
this method is still not asynchronous.
All we have done is,
we changed the declaration of the method,
what we're essentially calling asynchronous blocking operation here and here.
So we need to change these two blocking operations to asynchronous ones.
Now, since.NET 4.5, pretty much most methods that are
blocking operations have an asynchronous or nonblocking version,
and they all end with the async suffix.
So, let's have a look here.
So in the WebClient class,
we have DownloadString which is the synchronous version,
and we have TaskAsync and Async.
This async method here is a legacy one and it's got nothing to do with
the new asynchronous programming model in.NET 4.5.
So, this is the one we're going to use.
And as we see,
it returns a Task of string because the original method returned a string.
Now the asynchronous version returns a Task of a string.
So we're going to use this method here.
And typically, when we call an asynchronous method that returns a task we
need to put an await operator here.
What does it mean?
In the first glance,
it may give we the impression that
the program execution has to wait for this method to complete.
But that's not the case at all.
This is just a marker for the compiler.
So when the compiler sees that,
it knows that this operation is going to be costly,
and it may take a bit of time.
In that case, instead of blocking this thread,
it's going to return the control immediately to the color of this method here.
So the thread here is not going to be blocked and the control immediately returns here.
And here we exec this button underline
click method which means that the UI immediately becomes responsive.
Now, at some point, this method DownloadStringTaskAsync is going to be completed,
and the runtime is going to be aware of that because we marked this with await.
So when this method is completed,
runtime comes back here and executes the rest of this method.
So the interesting thing here is if we look,
compare these two methods,
they look pretty much the same,
except that, in this method we have an await here,
whereas we don't have that here in the original synchronous version.
But at runtime, how this code is executed looks different.
It's like, we have two different methods.
One is, one that includes only these two lines.
And there is another method that is a callback once DownloadStringTaskAsync is completed.
In that case, that method will be executed.
We as programmers do not have to partition
our code in terms of functions and their callbacks,
and we are giving this hard task to the compiler by using the async and await keywords.
Now interestingly,
this StreamWriter has a Write method here which is again a blocking operation.
So we can improve the responsiveness of our application even
further by using the asynchronous version of write method.
So, look, we have Write,
WriteAsync, WriteLine and WriteLineAsync.
So pretty much, as we see,
for all synchronous methods we have an asynchronous version.
I'm going to use the async one.
And as I explained, we need to put await
here to let the compiler know that this method is going to take some time.
So it returns to control immediately,
and the executing thread is not going to be blocked.
Now, in the button underline click,
let me call the asynchronous version of this method and see how it makes a difference.
So, this time I'm going to click this button and note that the window is
not going to be frozen and I can immediately move it around. So, click.
See, it's very responsive.
One more time, it's responsive.
Let's close this. Get back to our original synchronous method.
I click this button,
it's not moving, it's not.
It just move now because the synchronous operation completed.
So the use case for asynchronous programming is,
if we're building WPF applications or applications for the Windows Runtime,
wherever we have blocking operations like accessing files,
accessing database, calling Web services or accessing Web as we see here,
accessing the calendar, address book,
on a Windows mobile,
all of these are blocking operations and we can improve
the responsiveness of wer application by using async and await.
What about Web applications like asp.net mvc applications.
Well, in those applications,
the UI is not in the same process.
It's on the client's machine, in the browser.
So does the new async programming model improve web applications?
Yes. How? Well, typically in a web application,
when a request comes to the server,
a thread is allocated to handle that request.
Now, during execution of that request,
if there is a blocking operation,
that thread is going to be busy.
And each machine as we know,
has a limited number of threads.
So if we have a lot of concurrent connections,
and all our threads are busy waiting for a blocking operation,
that server becomes unresponsive.
And the only way is to add more servers,
which is scaling out.
We can improve this by using an asynchronous model.
So when a thread has to execute a blocking operation,
the control immediately returns to the thread,
and that thread can be used to handle another request.
When that blocking operation completes execution,
again the same thread or another thread will come back
here and pick up the rest of the program and continue execution.
So with this model, we can scale up instead of scaling out.
That doesn't mean that if we design
wer application poorly this is going to help we significantly.
Not at all. But this is just a new practice and a recommended practice,
so whenever we are using blocking operations,
we should use async and await.
Now, let's get back to our example here and see another use case.
This time I'm going to create a method that returns a string.
So instead of being void I want to return a string.
So, let's collapse these,
create a new method here.
"GetHtml" from a url.
Similarly, we're going to use a WebClient and
return webClient.DownloadString from that url.
So in the bottom underline click,
I'm going to call this method,
get the result and display it.
Sorry, I need to put the address here.
Okay.
Now, we got the Html and let's display it in a message box.
Now, that Html is going to be huge so I'm just going to get a substring of that.
Let's say the first 10 characters.
Let's run this application.
So, I click this button and notice there is going to be
a delay until we get the result and during that delay,
the window is going to be unresponsive.
So, can't move.
Now, we got the message box.
So, here's the beginning of the Html,
we click that, and now UI is responsive.
Let's make this asynchronous and improve the responsiveness of our application.
So, we start with async.
Instead of returning a string,
we need to return a Task of a string.
So a Task of a string,
call it "GetHtmlAsync", takes a URL.
I'm going to copy-paste this code into here.
Now this time, instead of calling DownloadString which is a blocking operation,
I'm going to call DownloadStringTaskAsync.
And as we said, this method returns a Task of string as we see here.
So we need to await that to tell
the runtime not to wait for the result of this method and continue execution.
Okay. Now, here in button underline click where we call GetHtml,
we're gonna replace this with GetHtmlAsync.
Now, the compiler is complaining.
Why? Because this HTML is a Task of string,
it's not the end result.
It's a Task object that represents the state of an asynchronous operation.
So, it doesn't have methods like Substring.
So, we need to await that here to get the actual string.
But interestingly, we got a red error here. Let's see what is here.
It says that, "await operator can only be used in a method
or lambda marked with the async modifier". What does it mean?
Here, we are awaiting for an asynchronous operation
but this method is not marked with async.
So, we need to change that to async.
And now the error is gone.
So the lesson is, we can only use the await keyword
or the await operator in an async method.
Let's run the application. Click the button.
We know it's responsive.
Now, we got a message.
Let me show we something else here.
We don't always have to await this asynchronous method straight away.
Let's see what happens if we don't do that.
So, I'm going to remove this.
I know, this object is not the Html, it's a Task.
So, let's rename it to Task of — let's call it GetHtmlTask.
And here, I can say the actual Html is await "getHtmlTask". What does this mean?
Well, when we call this method,
the control immediately returns here,
so we have a Task object that represents the state of that asynchronous operation.
Next week, I'm here and we're telling the runtime the rest of this method cannot be
executed until this operation is completed.
So the control immediately returns to the UI.
And that's why the UI is responsive.
But when that operation is completed,
the rest of this code is going to be executed.
At this point we get the Html and would display the message here.
Now what happens if we put a message box here?
Let's say, "Waiting for the task to complete".
Now, with this code,
as soon as we call this method control comes here immediately.
We get this message, and then UI becomes responsive.
Once the Html is downloaded,
then we get another message.
So, let's run the application.
Look, I click this button,
we immediately got a message.
Now the task completed,
and we got another message.
So, what I'm going to tell we here is,
we don't always have to await in asynchronous operation,
and we can do instead,
some work in between that is not dependent on the result of that asynchronous operation.
So this way, we can utilize a thread to its fullest potential.
We use await when the rest of that method cannot be executed until the result is ready.
Learning Paths

This course is part of a series of courses that help we master C#. Once we're proficient in C#,
then we can focus on specific areas such as web, mobile and game development depending
on what wer goals and interests are.

Here is the learning path that I recommend to we to get the most out of my courses:

Essentials

These courses are absolutely essential and we should take them in the following order. Do not
skip any of them!

 C# Basics for Beginners


 C# Intermediate: Classes, Interfaces and Object-oriented Programming (this course)
 C# Advanced

Mobile Development

Once we master C#, if we'd like to learn how to build mobile apps with C#, we can take the
following course:

 Xamarin Forms

Web (Back-end) Development


Alternatively, if we'd like to focus on web application development and become a back-end
developer, take the following courses:

 Entity Framework 6
 ASP.NET MVC 5

Optional but Recommended

If we'd like to become a serious developer, I highly encourage we to take the following
courses too. These courses help we become a better developer and write better code and in
less time:

 Double Wer Coding Speed


 Clean Code: The Art of Writing Beautiful C# Code
 Unit Testing C# Code

You might also like