Modello a oggetti LINQ to SQL

In LINQ to SQL, un modello a oggetti espresso nel linguaggio di programmazione dello sviluppatore viene mappato al modello dati di un database relazionale. Le operazioni sui dati vengono quindi eseguite in base al modello a oggetti.

In questo scenario non vengono eseguiti comandi di database, ad esempio INSERT, sul database, bensì vengono modificati valori ed eseguiti metodi all'interno del modello a oggetti. Quando si vuole eseguire una query sul database o inviare modifiche al database, LINQ to SQL converte le richieste in comandi SQL corretti che vengono quindi inviati al database.

Screenshot that shows the Linq Object Model.

Nella tabella seguente sono riepilogati gli elementi più importanti nel modello a oggetti di LINQ to SQL e le relative relazioni con gli elementi nel modello dati relazionale:

Modello a oggetti LINQ to SQL Modello dati relazionale
Classe di entità Tabella
Membro di classe Istogramma
Associazione Relazione di chiave esterna
metodo Stored procedure o funzione

Nota

Nelle descrizioni seguenti si presuppone una conoscenza di base del modello dati relazionale e delle regole.

Classi di entità LINQ to SQL e tabelle di database

In LINQ to SQL una tabella di database è rappresentata da una classe di entità. Una classe di entità è analoga a qualsiasi altra classe creata dallo sviluppatore, con l'eccezione che per annotare la classe vengono usate informazioni speciali che associano la classe a una tabella di database. Per creare tale annotazione, aggiungere un attributo personalizzato (TableAttribute) alla dichiarazione della classe, come nell'esempio seguente:

Esempio

[Table(Name = "Customers")]
public class Customerzz
{
    public string CustomerID;
    // ...
    public string City;
}
<Table(Name:="Customers")> _
Public Class Customer
    Public CustomerID As String
    ' ...
    Public City As String
End Class

Solo le istanze delle classi dichiarate come tabelle, ovvero le classi di entità, possono essere salvate nel database.

Per altre informazioni, vedere la sezione relativa all'attributo Table in Mapping basato su attributi.

Membri di classe LINQ to SQL e colonne di database

Oltre all'associazione delle classi con le tabelle, è necessario definire i campi o le proprietà per rappresentare le colonne del database. A questo scopo in LINQ to SQL viene definito l'attributo ColumnAttribute, come nell'esempio seguente:

Esempio

[Table(Name = "Customers")]
public class Customer
{
    [Column(IsPrimaryKey = true)]
    public string CustomerID;
    [Column]
    public string City;
}
<Table(Name:="Customers")> _
Public Class Customer
    <Column(IsPrimaryKey:=True)> _
    Public CustomerID As String

    <Column()> _
    Public City As String
End Class

Solo i campi e le proprietà di cui è stato eseguito il mapping alle colonne vengono salvati in modo permanente o recuperati dal database. Quelli non dichiarati come colonne vengono considerati parti temporanee della logica dell'applicazione.

All'attributo ColumnAttribute sono associate diverse proprietà che è possibile usare per personalizzare i membri che rappresentano colonne, ad esempio definendo un membro che rappresenta una colonna di chiave primaria. Per altre informazioni, vedere la sezione relativa all'attributo Column in Mapping basato su attributi.

Associazioni LINQ to SQL e relazioni di chiave esterna del database

In LINQ to SQL per rappresentare associazioni di database, ad esempio relazioni da chiave esterna a chiave primaria, viene applicato l'attributo AssociationAttribute. Nel segmento di codice seguente la classe Order contiene una proprietà Customer con un attributo AssociationAttribute. Questa proprietà e il relativo attributo forniscono la classe Order con una relazione alla classe Customer.

Nell'esempio di codice riportato di seguito viene illustrata la proprietà Customer della classe Order.

Esempio

[Association(Name="FK_Orders_Customers", Storage="_Customer", ThisKey="CustomerID", IsForeignKey=true)]
public Customer Customer
{
    get
    {
        return this._Customer.Entity;
    }
    set
    {
        Customer previousValue = this._Customer.Entity;
        if (((previousValue != value)
                    || (this._Customer.HasLoadedOrAssignedValue == false)))
        {
            this.SendPropertyChanging();
            if ((previousValue != null))
            {
                this._Customer.Entity = null;
                previousValue.Orders.Remove(this);
            }
            this._Customer.Entity = value;
            if ((value != null))
            {
                value.Orders.Add(this);
                this._CustomerID = value.CustomerID;
            }
            else
            {
                this._CustomerID = default(string);
            }
            this.SendPropertyChanged("Customer");
        }
    }
}
<Association(Name:="FK_Orders_Customers", Storage:="_Customer", ThisKey:="CustomerID", IsForeignKey:=true)>  _
Public Property Customer() As Customer
    Get
        Return Me._Customer.Entity
    End Get
    Set
        Dim previousValue As Customer = Me._Customer.Entity
        If (((previousValue Is value)  _
                    = false)  _
                    OrElse (Me._Customer.HasLoadedOrAssignedValue = false)) Then
            Me.SendPropertyChanging
            If ((previousValue Is Nothing)  _
                        = false) Then
                Me._Customer.Entity = Nothing
                previousValue.Orders.Remove(Me)
            End If
            Me._Customer.Entity = value
            If ((value Is Nothing)  _
                        = false) Then
                value.Orders.Add(Me)
                Me._CustomerID = value.CustomerID
            Else
                Me._CustomerID = CType(Nothing, String)
            End If
            Me.SendPropertyChanged("Customer")
        End If
    End Set
End Property

Per altre informazioni, vedere la sezione relativa all'attributo Association di Mapping basato su attributi.

Metodi LINQ to SQL e stored procedure di database

LINQ to SQL supporta stored procedure e funzioni definite dall'utente. In LINQ to SQL viene eseguito il mapping di queste astrazioni definite dal database agli oggetti client, in modo che sia possibile accedervi in modo fortemente tipizzato dal codice client. Le firme del metodo sono quanto più possibile simili alle firme delle procedure e delle funzioni definite nel database. Per individuare questi metodi è possibile usare IntelliSense.

Un set di risultati restituito da una chiamata a una procedura con mapping è una raccolta fortemente tipizzata.

LINQ to SQL esegue il mapping di stored procedure e funzioni ai metodi usando gli attributi FunctionAttribute e ParameterAttribute. I metodi che rappresentano stored procedure si differenziano da quelli che rappresentano funzioni definite dall'utente per la proprietà IsComposable. Se questa proprietà è impostata su false, che corrisponde all'impostazione predefinita, il metodo rappresenta una stored procedure. Se è impostata su true, il metodo rappresenta una funzione di database.

Nota

Se si usa Visual Studio, è possibile usare Object Relational Designer per creare metodi mappati a stored procedure e funzioni definite dall'utente.

Esempio

// This is an example of a stored procedure in the Northwind
// sample database. The IsComposable property defaults to false.
[Function(Name="dbo.CustOrderHist")]
public ISingleResult<CustOrderHistResult> CustOrderHist([Parameter(Name="CustomerID", DbType="NChar(5)")] string customerID)
{
    IExecuteResult result = this.ExecuteMethodCall(this, ((MethodInfo)(MethodInfo.GetCurrentMethod())), customerID);
    return ((ISingleResult<CustOrderHistResult>)(result.ReturnValue));
}
   ' This is an example of a stored procedure in the Northwind
   ' sample database. The IsComposable property defaults to false.
   <FunctionAttribute(Name:="dbo.CustOrderHist")> _
Public Function CustOrderHist(<Parameter(Name:="CustomerID", DbType:="NChar(5)")> ByVal customerID As String) As ISingleResult(Of CustOrderHistResult)
       Dim result As IExecuteResult = Me.ExecuteMethodCall(Me, CType(MethodInfo.GetCurrentMethod, MethodInfo), customerID)
       Return CType(result.ReturnValue, ISingleResult(Of CustOrderHistResult))
   End Function

Per altre informazioni, vedere le sezioni relative agli attributi Function, Stored Procedure e Parameter in Mapping basato su attributi e Stored procedure.

Vedi anche