Introduzione a C#

97
Introduzione a C# 1 Introduzione a C# Carlo Becchi [email protected]

description

Introduzione a C#. Carlo Becchi [email protected]. C#: Strumento Principe per .net. Primo linguaggio orientato alle componenti della famiglia C/C++ Tutto è DAVVERO un oggetto Unisce potenza, semplicità e chiarezza di C++, Java, VB… Completamente nuovo, non ha vincoli con il passato. - PowerPoint PPT Presentation

Transcript of Introduzione a C#

Page 1: Introduzione a C#

Introduzione a C#

1

Introduzione a C#

Carlo [email protected]

Page 2: Introduzione a C#

Introduzione a C#

2

C#: Strumento Principe per .net

• Primo linguaggio orientato alle componenti della famiglia C/C++

• Tutto è DAVVERO un oggetto• Unisce potenza, semplicità e

chiarezza di C++, Java, VB…• Completamente nuovo, non ha

vincoli con il passato

Page 3: Introduzione a C#

Introduzione a C#

3

C#: Strumento Principe per .net

• Indipendente dalla piattaforma e scalabile

• “Nato con” e “cucito addosso” al .NET Framework

• Può essere integrato nelle pagine web

• Completamente Type Safe

Page 4: Introduzione a C#

Introduzione a C#

4

C#: Strumento Principe per .net

• Standardizzato dall’ECMA• Ideato da Anders Hejlsberg e

dal team di J++

Page 5: Introduzione a C#

Introduzione a C#

5

In principio fu System.Object

Page 6: Introduzione a C#

Introduzione a C#

6

Tutto è un oggetto• In C# tutti i tipi reference, sono

derivati dal tipo base System.Object.

• Ogni oggetto eredita i metodi base da System.Object

… ma proprio OGNI* tipo…

*Mediante il meccanismo di Boxing

Page 7: Introduzione a C#

Introduzione a C#

7

Tutto è un oggettousing System;class Test{static void Main() {Console.WriteLine(3.ToString());}}

ToString restituisce una stinga che rappresenta il valoredell’oggetto

Page 8: Introduzione a C#

Introduzione a C#

8

Tutto è un oggetto

In particolare la classe System.Object offre i seguenti metodi:

Equals (public, virtual): Permette la comparazione di due oggetti per stabilire se il loro valore è uguale.

GetHashCode (public, virtual): Permette ai tipi di restituire un integer a 32bit con segno come codice hash per i suoi oggetti. Si solito viene utilizzato per memorizzare oggetti in una tabella hash.

ToString (public, virtual): Permette ad un tipo di fornire in ritorno una stringa che rappresenta il valore dell’oggetto.

GetType (public, non-virtual): Restituisce un oggetto che rappresenta il tipo dell’oggetto.

MemberwiseClone (protected, non-virtual): Permette al tipo di costruire una nuova istanza che è copia di se stesso.

Finalize (protected, virtual): Permette di ripulire dalla memoria gli oggetti del tipo e rilasciare le risorse associate.

Page 9: Introduzione a C#

Introduzione a C#

9

Tutto è un oggettousing System;

public class MyClass

{

public static void Main()

{

object a;

a = 1; // un esempio di boxing

Console.WriteLine(a);

Console.WriteLine(a.GetType());

Console.WriteLine(a.ToString());

Console.WriteLine();

}

}

Output1System.Int321

Page 10: Introduzione a C#

Introduzione a C#

10

Hello, World!

Page 11: Introduzione a C#

Introduzione a C#

11

Hello, World!• Si utilizza il metodo WriteLine

della classe Console, presente nel namespace System contenuto nell’assembly mscorlib.dll.

• Salutiamo il mondo in C#, VB e C++

Page 12: Introduzione a C#

Introduzione a C#

12

Hello, World: C#// Permette riferimenti semplificati al namespace System

using System;

// Questa classe esiste solo per ospitare la funzione entry point dell'applicazione

class MainApp {

// Il metodo statico Main è l'entry point dell'applicazione

public static void Main() {

// Scrive il testo sulla console

Console.WriteLine("Hello World using C#!");

}

}

Page 13: Introduzione a C#

Introduzione a C#

13

Hello, World: VB' Permette riferimenti semplificati al namespace System

Imports System

' Il Module ospita l'entry point dell'applicazione

Public Module modmain

' "Main" è l'entry point dell'applicazione

Sub Main()

' Scrive il testo sulla console

Console.WriteLine ("Hello World using Visual Basic!")

End Sub

End Module

Page 14: Introduzione a C#

Introduzione a C#

14

Hello, World: C++// L'utilizzo dell'assemby mscorlib.dll deve essere specificato!

#using <mscorlib.dll>

// Permette riferimenti semplificati al namespace System

using namespace System;

// La global function "main" è l'entry point dell'applicazione

void main() {

// Scrive il testo sulla console

Console::WriteLine("Hello World using Managed Extensions for C++!");

}

Page 15: Introduzione a C#

Introduzione a C#

15

Sviluppo Cross Language

Page 16: Introduzione a C#

Introduzione a C#

16

Sviluppo Cross Language• L’interoperabilità tra linguaggi

aderenti al CLS è immediata• Da una classe base scritta in C+

+ ne sarà derivata una in VB, dalla quale ne sarà derivata una in IL e da C#…

Page 17: Introduzione a C#

Introduzione a C#

17

VCBase.cpp#using <mscorlib.dll>using namespace System;

public class VCBase{protected: VCBase(){ Console::WriteLine(" Executing the VCBase::VCBase() constructor"); }

public: virtual void Method() = 0; void MethodThatThrows(){ throw(new OutOfMemoryException("We are out of some resource!")); }

};

Page 18: Introduzione a C#

Introduzione a C#

18

VBDerived.vbOption Explicit On Option Strict On

Imports System

Public Class VBDerived Inherits VCBase

Public Sub New()

Console.WriteLine(" Executing the VBDerived.New() constructor")

End Sub

Overrides Public Sub Method Console.WriteLine(" Executing the VBDerived.Method() virtual method") End Sub

End Class

Page 19: Introduzione a C#

Introduzione a C#

19

ILDerived.il.module extern VBDerived.netmodule

.class public auto ansi ILDerived extends [.module VBDerived.netmodule]VBDerived{ .method public specialname rtspecialname instance void .ctor() il managed { .maxstack 1 .locals init (class System.Object[] V_0) IL_0000: ldarg.0 IL_0001: call instance void [.module VBDerived.netmodule]VBDerived::.ctor() IL_0006: ldstr " Executing the ILDerived::ctor() constructor" IL_000b: call void [mscorlib]System.Console::WriteLine(class System.String) IL_0010: ret }

.method public virtual instance void Method() il managed { .maxstack 1 .locals init (class System.Object[] V_0) IL_0000: ldstr " Executing the ILDerived::Method() virtual method" IL_0005: call void [mscorlib]System.Console::WriteLine(class System.String) IL_000a: ret }}

Page 20: Introduzione a C#

Introduzione a C#

20

CSDerived.csusing System;

public class CSDerived:ILDerived{ public CSDerived(){ Console.WriteLine("Executing the CSDerived.CSDerived() constructor"); }

override public void Method(){ Console.WriteLine(" Executing the CSDerived.Method() virtual method"); }}

Page 21: Introduzione a C#

Introduzione a C#

21

CrossLang.cs

class App{ public static void Main(){ CrossObj(); } static void CrossObj(){ // Crea un array di oggetti per immagazzinare quelli definiti //negli altri linguaggi VCBase[] objects = new VCBase[3];

// Carica nella posizione 0 dell'array l'oggetto //creato usando IL Console.WriteLine("\nCreating object: ILDerived"); objects[0] = new ILDerived();

// Carica nella posizione 1 dell'array l'oggetto //creato usando C# Console.WriteLine("\nCreating object: CSDerived"); objects[1] = new CSDerived();

// Carica nella posizione 2 dell'array l'oggetto //creato usando VB Console.WriteLine("\nCreating object: VBDerived"); objects[2] = new VBDerived();

// Chiama il metodo virtuale di ogni oggetto Console.WriteLine("\nCalling Methods"); foreach(VCBase obj in objects){ obj.Method(); } } }

Page 22: Introduzione a C#

Introduzione a C#

22

Page 23: Introduzione a C#

Introduzione a C#

23

Boxing ed Unboxing dei Value

Page 24: Introduzione a C#

Introduzione a C#

24

Boxing ed Unboxing dei Value

• Il Boxing dei value è un concetto essenziale nel sistema dei tipi del C#. Con il boxing e l’unboxing si può realizzare un collegamento tra i value type e i reference type permettendo che il valore di un value type sia convertito da e verso un oggetto.

• Convertire un value type in un reference type è detto Boxing, il processo inverso Unboxing.

• Il Boxing avviene automaticamente quando un value type è utilizzato in una locazione che richiederebbe l’uso di un oggetto. Il Boxing di un value type consiste nell’allocare l’istanza di un oggetto e copiare il valore nell’istanza.

Page 25: Introduzione a C#

Introduzione a C#

25

Boxing ed Unboxing dei Value

using System;class Test{static void Main() {int i = 1;object o = i; // boxing// verifica che o sia davvero un intif (o is int) {Console.Write("O is an int");}

int j = (int) o; // unboxing}}

Page 26: Introduzione a C#

Introduzione a C#

26

Boxing ed Unboxing dei Value

Page 27: Introduzione a C#

Introduzione a C#

27

Boxing ed Unboxing dei Value

Page 28: Introduzione a C#

Introduzione a C#

28

Boxing ed Unboxing dei Valueusing System;

public class UnboxingTest

{

public static void Main()

{ int intI = 123;

object o = intI;

// Riferimenti a oggetti incompatibili producono

// InvalidCastException

try

{

int intJ = (short) o;

Console.WriteLine("Unboxing OK.");

}

catch (InvalidCastException e)

{

Console.WriteLine("{0} Error: Incorrect unboxing.",e);

} } }

Boxing Scorretto:Errore di Runtime

Page 29: Introduzione a C#

Introduzione a C#

29

Differenze tra Value e Reference Type

Page 30: Introduzione a C#

Introduzione a C#

30

Differenze tra Value e Reference Type

• Reference Type allocati nel Managed Heap, l’operatore restituisce l’indirizzo di memoria dell’oggetto (GC)

• Value Type allocati nello stack del thread, la variabile che rappresenta l’oggetto ne contiene direttamente il valore (nessuna GC)

Page 31: Introduzione a C#

Introduzione a C#

31

Differenze tra Value e Reference Typeusing System;

// E' un tipo Reference (a causa del 'class')class RefType { public int x; }

// E' un tipo Value (a causa del 'struct')struct ValType { public int x; }

class App { static void Main() { RefType rt1 = new RefType(); // Allocato nell'heap ValType vt1 = new ValType(); // Allocato nello stack rt1.x = 10; // Cambia il riferimento a cui punta vt1.x = 10; // Cambiato il valore nello stack

RefType rt2 = rt1; // Copia il solo puntatore ValType vt2 = vt1; // Alloca nello stack e copia i membri rt1.x = 20; vt1.x = 20; Console.WriteLine("rt1.x = {0}, rt2.x = {1}", rt1.x, rt2.x); Console.WriteLine("vt1.x = {0}, vt2.x = {1}", vt1.x, vt2.x);

Console.Write("Press Enter to close window..."); Console.Read(); } }

Page 32: Introduzione a C#

Introduzione a C#

32

Differenze tra Value e Reference Type

Page 33: Introduzione a C#

Introduzione a C#

33

Differenze tra Value e Reference Type RefType rt1 = new RefType(); ValType vt1 = new ValType(); rt1.x = 10; vt1.x = 10;

RefType rt2 = rt1; ValType vt2 = vt1; rt1.x = 20; vt1.x = 20;

rt1.x

vt1.x

vt2.x

rt2.x

10

20

10

10

rt1.x

vt1.x 20

rt2.x

Page 34: Introduzione a C#

Introduzione a C#

34

Delegate

Page 35: Introduzione a C#

Introduzione a C#

35

Delegate• Un oggetto delegate contiene informazioni

necessarie a richiamare uno specifico metodo di un dato oggetto.

• Corrispondente “Type Safe” e Object oriented del Function Pointer

• Permettono l’esecuzione dei Callback in maniera sicura

• Sono definiti in runtime e si riferiscono solo a metodi e non ad una intera classe.

Page 36: Introduzione a C#

Introduzione a C#

36

Delegate• Un istanza di un delegate incapsula uno o più

metodi, ognuno noto come callable entity.• L’oggetto delegate può essere passato al

codice che richiama il metodo in esso incapsulato senza sapere in compile time quale metodo sarà invocato.

• L’unica cosa che richiede al metodo che incapsula è di essere compatibile con il tipo del delegate

Page 37: Introduzione a C#

Introduzione a C#

37

Delegate

delegate void SimpleDelegate();

Dichiarazione

class Test{

static void A() {System.Console.WriteLine("Test.A");

}static void Main() {

SimpleDelegate d = new SimpleDelegate(A);d();

}}

Page 38: Introduzione a C#

Introduzione a C#

38

Delegatevoid MultiCall(SimpleDelegate d, int count) {

for (int i = 0; i < count; i++)d();

}}• Il metodo Multicall non considera il tipo del metodo di destinazione

per il delegate SimpleDelegate, la sua accessibilità o il fatto che esso sia o meno statico. Tutto ciò che importa che sia compatibile con SimpleDelegate

Page 39: Introduzione a C#

Introduzione a C#

39

class DChatServer { public delegate void OnMsgArrived(String message); private static OnMsgArrived onMsgArrived; private DChatServer() {} public static void ClientConnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Combine(DChatServer.onMsgArrived, onMsgArrived); } public static void ClientDisconnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Remove(DChatServer.onMsgArrived, onMsgArrived); } public static void SendMsg(String msg) { // Invia un messaggio a TUTTI i client SendMsg(msg, null); } public static void SendMsg(String msg, Object excludeClient) { // Invia un messaggio a tutti i client tranne 'excludeClient' if (excludeClient == null) { onMsgArrived(msg); } else { Delegate[] DelegateList = onMsgArrived.GetInvocationList(); for (int i = 0; i < DelegateList.Length; i++) { if (DelegateList[i].Target != excludeClient) { ((OnMsgArrived) DelegateList[i])(msg);

} } } } }

Page 40: Introduzione a C#

Introduzione a C#

40

class DChatClient { private void onMsgArrived(String msg) { Console.WriteLine("Msg arrived (Client {0}): {1}", clientName, msg); }

private String clientName;

public DChatClient(String clientName) { this.clientName = clientName; DChatServer.ClientConnect(new DChatServer.OnMsgArrived(onMsgArrived)); }

public void Dispose() { DChatServer.ClientDisconnect(new DChatServer.OnMsgArrived(onMsgArrived)); GC.SuppressFinalize(this); }

~DChatClient() { Dispose(); }}

Page 41: Introduzione a C#

Introduzione a C#

41

private static void DelegateChatServerDemo() { Console.WriteLine("Demo start: Delegate Chat Server.");

DChatClient cc1 = new DChatClient("1"); DChatClient cc2 = new DChatClient("2"); DChatClient cc3 = new DChatClient("3");

DChatServer.SendMsg("Hi to all clients"); DChatServer.SendMsg("Hi to all clients except client 2", cc2);

// Sconnette esplicitamente i client dal chat server. // Se questo non viene fatto, la memoria dei client potrebbe // non essere liberata finché il server attivo, ovvero fino // alla chiusura dell'applicazione

cc1.Dispose(); cc2.Dispose(); cc3.Dispose(); Console.WriteLine("Demo stop: Delegate Chat Server."); }

Page 42: Introduzione a C#

Introduzione a C#

42

class DChatServer { public delegate void OnMsgArrived(String message); private static OnMsgArrived onMsgArrived; private DChatServer() {} public static void ClientConnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Combine(DChatServer.onMsgArrived, onMsgArrived); } public static void ClientDisconnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Remove(DChatServer.onMsgArrived, onMsgArrived); } public static void SendMsg(String msg) { // Invia un messaggio a TUTTI i client SendMsg(msg, null); } public static void SendMsg(String msg, Object excludeClient) { // Invia un messaggio a tutti i client tranne 'excludeClient' if (excludeClient == null) { onMsgArrived(msg); } else { Delegate[] DelegateList = onMsgArrived.GetInvocationList(); for (int i = 0; i < DelegateList.Length; i++) { if (DelegateList[i].Target != excludeClient) { ((OnMsgArrived) DelegateList[i])(msg);} } } } }

Page 43: Introduzione a C#

Introduzione a C#

43

private static void DelegateChatServerDemo() { Console.WriteLine("Demo start: Delegate Chat Server.");

DChatClient cc1 = new DChatClient("1"); DChatClient cc2 = new DChatClient("2"); DChatClient cc3 = new DChatClient("3");

DChatServer.SendMsg("Hi to all clients"); DChatServer.SendMsg("Hi to all clients except client 2", cc2);

// Sconnette esplicitamente i client dal chat server. // Se questo non viene fatto, la memoria dei client potrebbe // non essere liberata finché il server attivo, ovvero fino // alla chiusura dell'applicazione

cc1.Dispose(); cc2.Dispose(); cc3.Dispose(); Console.WriteLine("Demo stop: Delegate Chat Server."); }

Page 44: Introduzione a C#

Introduzione a C#

44

class DChatClient { private void onMsgArrived(String msg) { Console.WriteLine("Msg arrived (Client {0}): {1}", clientName, msg); }

private String clientName;

public DChatClient(String clientName) { this.clientName = clientName; DChatServer.ClientConnect(new DChatServer.OnMsgArrived(onMsgArrived)); }

public void Dispose() { DChatServer.ClientDisconnect(new DChatServer.OnMsgArrived(onMsgArrived)); GC.SuppressFinalize(this); }

~DChatClient() { Dispose(); }}

Page 45: Introduzione a C#

Introduzione a C#

45

class DChatServer { public delegate void OnMsgArrived(String message); private static OnMsgArrived onMsgArrived; private DChatServer() {} public static void ClientConnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Combine(DChatServer.onMsgArrived, onMsgArrived); } public static void ClientDisconnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Remove(DChatServer.onMsgArrived, onMsgArrived); } public static void SendMsg(String msg) { // Invia un messaggio a TUTTI i client SendMsg(msg, null); } public static void SendMsg(String msg, Object excludeClient) { // Invia un messaggio a tutti i client tranne 'excludeClient' if (excludeClient == null) { onMsgArrived(msg); } else { Delegate[] DelegateList = onMsgArrived.GetInvocationList(); for (int i = 0; i < DelegateList.Length; i++) { if (DelegateList[i].Target != excludeClient) { ((OnMsgArrived) DelegateList[i])(msg);} } } } }

Page 46: Introduzione a C#

Introduzione a C#

46

private static void DelegateChatServerDemo() { Console.WriteLine("Demo start: Delegate Chat Server.");

DChatClient cc1 = new DChatClient("1"); DChatClient cc2 = new DChatClient("2"); DChatClient cc3 = new DChatClient("3");

DChatServer.SendMsg("Hi to all clients"); DChatServer.SendMsg("Hi to all clients except client 2", cc2);

// Sconnette esplicitamente i client dal chat server. // Se questo non viene fatto, la memoria dei client potrebbe // non essere liberata finché il server attivo, ovvero fino // alla chiusura dell'applicazione

cc1.Dispose(); cc2.Dispose(); cc3.Dispose(); Console.WriteLine("Demo stop: Delegate Chat Server."); }

Page 47: Introduzione a C#

Introduzione a C#

47

class DChatServer { public delegate void OnMsgArrived(String message); private static OnMsgArrived onMsgArrived; private DChatServer() {} public static void ClientConnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Combine(DChatServer.onMsgArrived, onMsgArrived); } public static void ClientDisconnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Remove(DChatServer.onMsgArrived, onMsgArrived); } public static void SendMsg(String msg) { // Invia un messaggio a TUTTI i client SendMsg(msg, null); } public static void SendMsg(String msg, Object excludeClient) { // Invia un messaggio a tutti i client tranne 'excludeClient' if (excludeClient == null) { onMsgArrived(msg); } else { Delegate[] DelegateList = onMsgArrived.GetInvocationList(); for (int i = 0; i < DelegateList.Length; i++) { if (DelegateList[i].Target != excludeClient) { ((OnMsgArrived) DelegateList[i])(msg);} } } } }

Page 48: Introduzione a C#

Introduzione a C#

48

private static void DelegateChatServerDemo() { Console.WriteLine("Demo start: Delegate Chat Server.");

DChatClient cc1 = new DChatClient("1"); DChatClient cc2 = new DChatClient("2"); DChatClient cc3 = new DChatClient("3");

DChatServer.SendMsg("Hi to all clients"); DChatServer.SendMsg("Hi to all clients except client 2", cc2);

// Sconnette esplicitamente i client dal chat server. // Se questo non viene fatto, la memoria dei client potrebbe // non essere liberata finché il server attivo, ovvero fino // alla chiusura dell'applicazione

cc1.Dispose(); cc2.Dispose(); cc3.Dispose(); Console.WriteLine("Demo stop: Delegate Chat Server."); }

Page 49: Introduzione a C#

Introduzione a C#

49

class DChatClient { private void onMsgArrived(String msg) { Console.WriteLine("Msg arrived (Client {0}): {1}", clientName, msg); }

private String clientName;

public DChatClient(String clientName) { this.clientName = clientName; DChatServer.ClientConnect(new DChatServer.OnMsgArrived(onMsgArrived)); }

public void Dispose() { DChatServer.ClientDisconnect(new DChatServer.OnMsgArrived(onMsgArrived)); GC.SuppressFinalize(this); }

~DChatClient() { Dispose(); }}

Page 50: Introduzione a C#

Introduzione a C#

50

class DChatServer { public delegate void OnMsgArrived(String message); private static OnMsgArrived onMsgArrived; private DChatServer() {} public static void ClientConnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Combine(DChatServer.onMsgArrived, onMsgArrived); } public static void ClientDisconnect(OnMsgArrived onMsgArrived) { DChatServer.onMsgArrived = (OnMsgArrived) Delegate.Remove(DChatServer.onMsgArrived, onMsgArrived); } public static void SendMsg(String msg) { // Invia un messaggio a TUTTI i client SendMsg(msg, null); } public static void SendMsg(String msg, Object excludeClient) { // Invia un messaggio a tutti i client tranne 'excludeClient' if (excludeClient == null) { onMsgArrived(msg); } else { Delegate[] DelegateList = onMsgArrived.GetInvocationList(); for (int i = 0; i < DelegateList.Length; i++) { if (DelegateList[i].Target != excludeClient) { ((OnMsgArrived) DelegateList[i])(msg);} } } } }

Page 51: Introduzione a C#

Introduzione a C#

51

Delegate

Page 52: Introduzione a C#

Introduzione a C#

52

MultiThread

Page 53: Introduzione a C#

Introduzione a C#

53

• Essendo la gestione dei processi gestita dal CLR, l’accesso a queste funzionalità da C# è molto semplice

• Il namespace System.Threading fornisce metodi per creare, eseguire, gestire e sincronizzare thread

MultiThread

Page 54: Introduzione a C#

Introduzione a C#

54

MultiThreadusing System;using System.Threading;

class App { //Codice del metodo eseguito nel primo Thread public static void MyThreadMethod1() { for ( int i = 0; i<=30; i++ ) { Console.WriteLine("thread 1");

} } //Codice del metodo eseguito nel secondo Thread public static void MyThreadMethod2() { for ( int j = 0; j<=30; j++ ) { Console.WriteLine("thread 2");

} }

Page 55: Introduzione a C#

Introduzione a C#

55

MultiThreadstatic void Main() { //Crea il primo thread Thread thread1 = new Thread(new ThreadStart(MyThreadMethod1)); //Avvia il primo thread thread1.Start(); //Crea il secondo thread Thread thread2 = new Thread(new ThreadStart(MyThreadMethod2)); //Avvia il secondo thread thread2.Start(); //Durante l'esecuzione dei 2 thread esegue un terzo ciclo for ( int i = 0; i<=30; i++ ) { Console.WriteLine("Main Thread");

} }}

Page 56: Introduzione a C#

Introduzione a C#

56

MultiThread

Page 57: Introduzione a C#

Introduzione a C#

57

Remoting

Page 58: Introduzione a C#

Introduzione a C#

58

Remoting• Il Remoting fornisce una struttura che consente agli

oggetti di interagire tra di loro anche se risiedono su diversi application domain

• La comunicazione avviene attraverso canali• Prima che i messaggi tra le applicazioni remote

vengano inviati sui canali vengono codificati:– In binario per le applicazioni critiche– In XML dove è essenziale interoperabilità

• I messaggi XML utilizzano sempre SOAP

Page 59: Introduzione a C#

Introduzione a C#

59

Remoting• I servizi di Remoting offerti dal framework

nascondono al programmatore la complessità dei metodi di chiamata remoti.

• Quando un client attiva un oggetto remoto ne riceve un proxy con il quale interagisce

• Per prima cosa si registra un canale di comunicazione (HTTP, TCP), poi diventa possibile registrare gli oggetti remoti

Page 60: Introduzione a C#

Introduzione a C#

60

Remoting• Per la registrazione di un oggetto remoto servono i

seguenti dati:– Il nome del tipo di oggetto remoto.

– L'oggetto URI (Uniform Resource Identifier) che i client utilizzeranno per individuare l'oggetto.

– La modalità oggetto richiesta per l'attivazione da server, che può essere

SingleCall o Singleton.

Page 61: Introduzione a C#

Introduzione a C#

61

Remoting• SigleCall

– Un oggetto SingleCall crea un'istanza di classe per ogni chiamata del client, anche

se le chiamate provengono dallo stesso client. – L'invocazione successiva, sarà sempre servita da una differente istanza del server

anche se la precedente non è stata ancora riciclata dal sistema.

• Singleton– Un oggetto Singleton invece non presenta mai più di una istanza

contemporaneamente

– Se una istanza è già esistente la richiesta viene soddisfatta da quella istanza. Se l'istanza non esiste, alla prima richiesta viene creata dal server e tutte le successive richieste vengono soddisfatte da quella istanza.

Page 62: Introduzione a C#

Introduzione a C#

62

server.cs

using System;using System.Runtime.Remoting;using System.Runtime.Remoting.Channels;using System.Runtime.Remoting.Channels.Tcp;

namespace RemotingSamples { public class Sample {

public static int Main(string [] args) { // Crea e registra un nuovo canale Tcp TcpChannel chan = new TcpChannel(8085); ChannelServices.RegisterChannel(chan); // Il metodo RegisterWellKnownServiceType permette di registrare l’oggetto per la // futura attivazione [PARAMETRI (Tipo, URI, metodo di attivazione)] RemotingConfiguration.RegisterWellKnownServiceType (Type.GetType("RemotingSamples.HelloServer,object"), "SayHello", WellKnownObjectMode.SingleCall); System.Console.WriteLine("Hit to exit..."); System.Console.ReadLine(); return 0; } }}

Page 63: Introduzione a C#

Introduzione a C#

63

object.cs

using System;using System.Runtime.Remoting;using System.Runtime.Remoting.Channels;using System.Runtime.Remoting.Channels.Tcp;

namespace RemotingSamples { public class HelloServer : MarshalByRefObject {

public HelloServer() { Console.WriteLine("HelloServer activated"); }

public String HelloMethod(String name) { Console.WriteLine("Hello.HelloMethod : {0}", name); return "Hi there " + name; } }}

Page 64: Introduzione a C#

Introduzione a C#

64

client.cs

using System;using System.Runtime.Remoting;using System.Runtime.Remoting.Channels;using System.Runtime.Remoting.Channels.Tcp;

namespace RemotingSamples { public class Client { public static int Main(string [] args) { TcpChannel chan = new TcpChannel(); ChannelServices.RegisterChannel(chan); // Il client localizza l’oggetto remoto passando tipo e URL HelloServer obj = (HelloServer)Activator.GetObject(typeof(RemotingSamples.HelloServer) , "tcp://localhost:8085/SayHello"); if (obj == null) System.Console.WriteLine("Could not locate server"); else Console.WriteLine(obj.HelloMethod("Carlo")); return 0; } }}

Page 65: Introduzione a C#

Introduzione a C#

65

Page 66: Introduzione a C#

Introduzione a C#

66

Accesso alle API di Windows

Page 67: Introduzione a C#

Introduzione a C#

67

Accesso alle API di Windows

using System; using System.Runtime.InteropServices;

class MainApp {

[DllImport("user32.dll", EntryPoint="MessageBox", SetLastError=true, CharSet=CharSet.Auto)] public static extern int MessageBox(int hWnd, String strMessage, String strCaption, uint uiType);

public static void Main() {

MessageBox( 0, "Saluti da WinAPI!", ".NET Tutorial", 0 ); }

}

Page 68: Introduzione a C#

Introduzione a C#

68

Accesso alle API di Windows

Page 69: Introduzione a C#

Introduzione a C#

69

Exceptiontry { // codice che può portare ad un errore}catch (Exception Type [ variable ]) { // codice che deve essere eseguito quando avviene l'errore}finally { // codice da eseguire che avvenga o meno // l'errore}

Page 70: Introduzione a C#

Introduzione a C#

70

Exceptionusing System;using System.IO;

public class App { public static void Main() { FileStream fs = null; try { fs = new FileStream(@"C:\NotThere.txt", FileMode.Open); } catch (Exception e) { Console.WriteLine(e.Message); } finally { if (fs != null) fs.Close(); } }}

Page 71: Introduzione a C#

Introduzione a C#

71

C# & ADO.NET

Interazione con i DataBase

Page 72: Introduzione a C#

Introduzione a C#

72

C# & ADO.NET

Page 73: Introduzione a C#

Introduzione a C#

73

C# & ADO.NET

Page 74: Introduzione a C#

Introduzione a C#

74

C# & ADO.NET

Page 75: Introduzione a C#

Introduzione a C#

75

C# & ADO.NET

Page 76: Introduzione a C#

Introduzione a C#

76

C# & ADO.NET

Page 77: Introduzione a C#

Introduzione a C#

77

Lettura dati da SQL Server

Page 78: Introduzione a C#

Introduzione a C#

78

using System;using System.Data.SqlClient;

public class Test{

public static void Main(){Test t=new Test();t.Run();}

public void Run(){SqlConnection conn = new SqlConnection("Data Source=BARIBAL; Integrated Security=SSPI; Initial Catalog=master");

SqlCommand cmd = new SqlCommand("SELECT * FROM emp_test", conn);try{ conn.Open();// Utilizziamo la classe DataReader per leggere la// tabella un record per volta, e via via stamparne// il contenuto sulla consoleSqlDataReader myReader = cmd.ExecuteReader();Console.WriteLine("Code \t Emp. Name \t Emp. Phone");Console.WriteLine("-----------------------------------------");

Page 79: Introduzione a C#

Introduzione a C#

79

// Ad ogni record letto...// (perchè in questo caso legge l'intera riga)while (myReader.Read()) { // ... estrae i valori e li stampa a schermo Console.WriteLine("{0}\t{1}\t\t{2}", myReader.GetInt32(0), myReader.GetString(1), myReader.GetString(2));

}// Chiude il DataReadermyReader.Close();// Chiude la Connessioneconn.Close();}catch(Exception e){Console.WriteLine("Exception Occured -->> {0}",e);}

}}

Page 80: Introduzione a C#

Introduzione a C#

80

Page 81: Introduzione a C#

Introduzione a C#

81

Lettura dati da SQL Servermediante OleDB Data

Provider

Page 82: Introduzione a C#

Introduzione a C#

82

using System;using System.Data.OleDb;

class OleDbTest{

public static void Main() { OleDbConnection aConnection = new OleDbConnection("Provider=SQLOLEDB.1; Persist Security Info=False; User ID=sa;Initial Catalog=northwind;Data Source=BARIBAL"); OleDbCommand aCommand = new OleDbCommand("select * from orders", aConnection); try{ aConnection.Open(); OleDbDataReader aReader = aCommand.ExecuteReader(); Console.WriteLine("This is the returned data from Northwind's Orders table"); while(aReader.Read()){ Console.WriteLine("{0}\t{1}", aReader.GetInt32(0),aReader.GetString(1)); } aReader.Close(); aConnection.Close(); } catch(OleDbException e) { Console.WriteLine("Error: {0}", e.Errors[0].Message); } }}

Page 83: Introduzione a C#

Introduzione a C#

83

Page 84: Introduzione a C#

Introduzione a C#

84

Alcune operazioni più avanzate

Modifiche al database “northwind” su SQL Server

Page 85: Introduzione a C#

Introduzione a C#

85

Popolare un DataSet// Crea un DataSet (una cache) per memorizzare i dati da elaborareDataSet objDataSet = new DataSet("OrderAdmin");

// Ora bisogna riempire la tabella, creando un// comando SELECT * dalla tabella Orders…string strOrders = "SELECT * FROM Orders ";SqlCommand objOrderCommand = new SqlCommand(strOrders,objSqlConnection);

// e un DataAdapter nel quale mappare la tabellaSqlDataAdapter objOrdAdapter = new SqlDataAdapter();objOrdAdapter.TableMappings.Add("Table","Orders");

// connettere il SqlCommand e l'SqlDataAdapterobjOrdAdapter.SelectCommand = objOrderCommand;

// e riempire il DataSet precedentemente creatoobjOrdAdapter.Fill(objDataSet);

Page 86: Introduzione a C#

Introduzione a C#

86

UpdateDataTable objOrdTable = objDataSet.Tables["Orders"];DataTable objODTable = objDataSet.Tables["Order Details"];// Ora aggiona il record della tabella Orders che ha OrderID=10248foreach(DataRow objRow in objOrdTable.Rows) {string strID = objRow["OrderID"].ToString(); string strShip = "HMS Invisible"; if(strID == "10248" ) {// Imposta le modifiche string strUpDate = "UPDATE Orders SET ShipName = "+"'"+strShip+"'"; strUpDate+=" WHERE OrderID = " + strID; objRow["ShipName"]=strShip ; // Crea il comando SQL appropriato per l'aggiornamento objOrdAdapter.UpdateCommand = new SqlCommand(strUpDate,objSqlConnection); // Esegue l'aggiornamento objOrdAdapter.Update(objDataSet,"Orders"); Console.WriteLine("Update done"); }}

Page 87: Introduzione a C#

Introduzione a C#

87

Cancellare un recordDataTable objOrdTable = objDataSet.Tables["Orders"];DataTable objODTable = objDataSet.Tables["Order Details"];// Cancella i record dalla tabella Order Details che hanno OrderID 10248for(int i=0;i<objODTable.Rows.Count;i++){// Crea un DataRow con l'i-esima riga della tabellaDataRow objDataRow = objODTable.Rows[i];string strID =objDataRow["OrderID"].ToString(); if( strID == "10248") {// se ha OrderID = 10248 cancella il record dal DataSet... objDataRow.Delete(); // ... ma solo dal DataSet! Per cancellarlo anche dalla sorgente dei dati, // il database memorizzato sul server, bisogna aggiornarlo con il contenuto // del dataset! objODAdapter.DeleteCommand = new SqlCommand("DELETE FROM [Order Details] WHERE OrderID = "+strID,objSqlConnection); objODAdapter.Update(objDataSet,"Order Details"); Console.WriteLine("Delete done"); }}

Page 88: Introduzione a C#

Introduzione a C#

88

Inserire un record// Inserisce un nuovo record nella tabella con OrderID = 10248// Per far questo si crea un oggetto DataRow con il metodo NewRow di DataTable,// si riempe la riga con i dati appropriati e la si inserisce in DataTable. DataRow objODRow = objODTable.NewRow(); objODRow["OrderID"] = 10248; objODRow["ProductID"] = 63; objODTable.Rows.Add(objODRow); // Ora aggiorniamo anche la sorgente... string strInsert = "INSERT INTO [Order Details] (OrderID,ProductID,UnitPrice,Quantity,Discount) VALUES(10248,63,33.4,100,0.20)"; objODAdapter.InsertCommand = new SqlCommand(strInsert,objSqlConnection); objODAdapter.Update(objDataSet,"Order Details"); Console.WriteLine("Insert done");

Page 89: Introduzione a C#

Introduzione a C#

89

Creare una relazioneDataColumn objDCParent;DataColumn objDCChild;

// Crea una DataRelation per collegare le tabelle Orders e Order DetailsDataRelation objDR;// Riempiamo i due DataColumn dichiarati in precedenzaobjDCParent=objDataSet.Tables["Orders"].Columns["OrderID"];objDCChild=objDataSet.Tables["Order Details"].Columns["OrderID"];// Per creare una relazione (DataRelation) denominata "OJoinOD" tra le due //colonne// OrderID delle tabelle Orders e Order DetailsobjDR=new DataRelation("OJoinOD", objDCParent,objDCChild);objDataSet.Relations.Add(objDR);

Page 90: Introduzione a C#

Introduzione a C#

90

Utilizzare la relazione

// Ora usiamo la relazione per stampare il ProductID prelevato da Order Details // alla quale si è acceduto fornendo l'OrderID della tabella Orders.// Al valore della colonna ProductID di Order Details ci si arriva seguendo la relazione.

// Per ogni riga nelle righe di Orders...foreach(DataRow objRow in objOrdTable.Rows) {//... se l'OrderID è pari a 10248... string strOrderID = objRow["OrderID"].ToString(); if(strOrderID=="10248") {//... Scrivi l'OrderID... Console.WriteLine("Order Id:"+strOrderID); // ... e per ogni riga nelle righe figlie della relazione OJoinOD... // (ovvero per ogni riga di Order Details che ha OrderID=10248) // (GetChildRows preleva le richieste righe figlie //del DataRow seguendo la relazione indicata)

foreach(DataRow objChild in objRow.GetChildRows(objDataSet.Relations["OJoinOD"])) {//... scrivi il ProductID string strProductID=objChild["ProductID"].ToString(); Console.WriteLine(strProductID); }

} }

Page 91: Introduzione a C#

Introduzione a C#

91

Page 92: Introduzione a C#

Introduzione a C#

92

Page 93: Introduzione a C#

Introduzione a C#

93..stavolta davvero!

Page 94: Introduzione a C#

Introduzione a C#

94

Bibliografia e Fonti>>In principio fu System.Object

*Documentazione Microsoft di accompagnamento

a .NET Framework SDK

>>Hello, World

*Documentazione Microsoft di accompagnamento

a .NET Framework SDK

>>Sviluppo Cross Language

*Documentazione Microsoft di accompagnamento

a .NET Framework SDK

>>Boxing ed Unboxing dei Value

*Documentazione Microsoft di accompagnamento

a .NET Framework SDK

*http://www.oreillynet.com/pub/a/dotnet/2001/06/07/csharp_java.html?page=4

*http://www.c-sharpcorner.com/Language/BoxNUnBoxGAG.asp

Page 95: Introduzione a C#

Introduzione a C#

95

Bibliografia e Fonti>>Differenza tra Value e Reference Type

*Documentazione Microsoft di accompagnamento

a .NET Framework SDK

>>Delegate

*Documentazione Microsoft di accompagnamento

a .NET Framework SDK

*http://www.ciol.com/content/technology/csharptutor/101103101.asp

*http://www.codeguru.com/cs_delegates/AS-Delegates.html

*http://www.devx.com/premier/mgznarch/vbpj/2001/09sep01/ce0109/ce0109-4.asp

*http://msdn.microsoft.com/msdnmag/issues/01/06/net/net0106.asp

Page 96: Introduzione a C#

Introduzione a C#

96

Bibliografia e Fonti>>MultiThread

*Documentazione Microsoft di accompagnamento

a .NET Framework SDK

*http://www.c-sharpcorner.com/2/mt_beginner1.asp

*http://www.oreillynet.com/pub/a/dotnet/2001/08/06/csharp.html

*http://www.csharphelp.com/archives/archive128.html

*http://www.codeproject.net/dotnet/multithread.asp

*http://www.crackinguniversity2000.it/dotnet/Visual%20Studio_NET%20_NET%20Framework.htm

>>Remoting

*http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dndotnet/html/hawkremoting.asp

>>C# & ADO .NET

*http://www.csharphelp.com/archives/archive103.html

*http://www.c-sharpcorner.com/Database/DBOpsInADOPA.asp

Tutti gli articoli citati sono di proprietà dei rispettivi autori.

Page 97: Introduzione a C#

Introduzione a C#

97

Credits• Progetto eseguito nell’ambito del corso

di “Basi di Dati”– Realizzato da Carlo Becchi – Tutor del progetto: Ing. Mauro Coccoli– Docente del corso: Prof. Antonio Boccalatte

• Laboratorio di Informatica DIST- Siemens/ORSI– http://www.lido.dist.unige.it

Aprile 2002