Matematica generica (panoramica), attributi generici (quando pertinenti)
Emulate la matematica generica senza funzionalità moderne: passate un provider di operazioni o dei delegate, applicate con attenzione i vincoli sui tipi e simulate i «generic attributes» tramite parametri Type.
Matematica generica (panoramica), attributi generici (quando pertinenti) è una lezione C# Academy gratuita su CoddyKit. Questa è la lezione 2 di 3. Puoi leggere la lezione completa qui gratuitamente — poi esercitati direttamente nel browser con un editor di codice integrato e un tutor IA disponibile 24/7. Fa parte del percorso di apprendimento C# Academy, e i tuoi progressi si sincronizzano tra il web e l'app CoddyKit. Il corso C# Academy include 3 lezioni in totale.
Calcolo generico in C# 6
Obiettivo: scrivere algoritmi numerici generici in C# 6.
- Nessun operatore statico astratto su T
- Soluzioni alternative: interfaccia ops-provider o piccoli delegati
- Per le annotazioni, utilizzi attributi con parametri Type
Pattern ops-provider
Fornisca Zero e Add tramite un'interfaccia. L'algoritmo generico chiama questi metodi invece di utilizzare + su T.
using System;
using System.Collections.Generic;
public interface INumericOps<T>
{
T Zero { get; }
T Add(T a, T b);
}
public sealed class IntOps : INumericOps<int>
{
public int Zero { get { return 0; } }
public int Add(int a, int b) { return a + b; }
}
public sealed class DoubleOps : INumericOps<double>
{
public double Zero { get { return 0.0; } }
public double Add(double a, double b) { return a + b; }
}
public class Program
{
static T Sum<T>(IEnumerable<T> items, INumericOps<T> ops)
{
T acc = ops.Zero;
foreach (T x in items) acc = ops.Add(acc, x);
return acc;
}
public static void Main(string[] args)
{
int s1 = Sum(new int[] {1,2,3}, new IntOps());
double s2 = Sum(new double[] {1.5, 2.0}, new DoubleOps());
Console.WriteLine("Sum int = " + s1);
Console.WriteLine("Sum double = " + s2);
}
}
Media con helper
Per le operazioni che non è possibile esprimere in modo generico (come la divisione), passi un piccolo convertitore o un delegato aggiuntivo.
using System;
using System.Collections.Generic;
public interface INumericOps<T>
{
T Zero { get; }
T Add(T a, T b);
}
public sealed class DoubleOps : INumericOps<double>
{
public double Zero { get { return 0.0; } }
public double Add(double a, double b) { return a + b; }
}
public class Program
{
static double Average<T>(IEnumerable<T> items, INumericOps<T> ops, Func<T,double> toDouble)
{
T acc = ops.Zero;
int count = 0;
foreach (T x in items) { acc = ops.Add(acc, x); count++; }
if (count == 0) throw new ArgumentException("Empty sequence", "items");
// convert with a delegate for division
return toDouble(acc) / count;
}
public static void Main(string[] args)
{
double avg = Average<double>(new double[] {2.0, 4.0, 6.0}, new DoubleOps(), delegate(double d) { return d; });
Console.WriteLine("Avg = " + avg);
}
}
Fold basato su delegato
I delegati mantengono il codice essenziale: passi un valore iniziale e una funzione di combinazione. È una soluzione adatta ai piccoli strumenti.
using System;
public class Program
{
static T Fold<T>(T[] xs, T seed, Func<T,T,T> combine)
{
T acc = seed;
for (int i = 0; i < xs.Length; i++) acc = combine(acc, xs[i]);
return acc;
}
public static void Main(string[] args)
{
int sum = Fold<int>(new int[] {1,2,3}, 0, delegate(int a, int b) { return a + b; });
double sumD = Fold<double>(new double[] {1.5, 2.5}, 0.0, delegate(double a, double b) { return a + b; });
Console.WriteLine("Sum ints = " + sum);
Console.WriteLine("Sum doubles = " + sumD);
}
}
Soluzione alternativa con attributi
In C# 6 non esistono veri attributi generici. Passi un Type all'attributo per indicare il tipo generico correlato.
using System;
using System.Reflection;
// C# 6 cannot declare generic attributes. Workaround: pass a Type.
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method)]
public sealed class ValidatorForAttribute : Attribute
{
public Type TargetType { get; private set; }
public ValidatorForAttribute(Type targetType) { TargetType = targetType; }
}
public sealed class Customer { public string Name; }
[ValidatorFor(typeof(Customer))]
public sealed class CustomerValidator
{
public bool IsValid(Customer c) { return c != null && !string.IsNullOrEmpty(c.Name); }
}
public class Program
{
public static void Main(string[] args)
{
Type t = typeof(CustomerValidator);
object[] attrs = t.GetCustomAttributes(typeof(ValidatorForAttribute), false);
if (attrs.Length > 0)
{
ValidatorForAttribute a = (ValidatorForAttribute)attrs[0];
Console.WriteLine("Validator targets: " + a.TargetType.Name);
}
}
}
Suggerimenti e scelte
Suggerimenti:
- Preferisca un ops-provider per gli algoritmi numerici riutilizzabili.
- Utilizzi i delegati per i piccoli helper (combinazione, conversione).
- Per le annotazioni, passi Type negli attributi e lo legga tramite reflection.
Soluzione alternativa per il calcolo generico
Riepilogo
Riepilogo: in assenza del calcolo generico moderno, passi ops o delegati agli algoritmi. Per le annotazioni, utilizzi attributi che contengono un Type e lo legga tramite reflection.
Domande Frequenti
La lezione «Matematica generica (panoramica), attributi generici (quando pertinenti)» è gratuita?
Sì — il testo completo di «Matematica generica (panoramica), attributi generici (quando pertinenti)» è gratuito qui sul web. Per esercitarvi in modo interattivo (un editor di codice integrato e un tutor IA 24/7) e sbloccare il resto del corso C# Academy, passa a CoddyKit PRO. Il corso C# Academy include 3 lezioni in totale.
Cosa imparerò in «Matematica generica (panoramica), attributi generici (quando pertinenti)»?
Emulate la matematica generica senza funzionalità moderne: passate un provider di operazioni o dei delegate, applicate con attenzione i vincoli sui tipi e simulate i «generic attributes» tramite para… Eserciti C# Academy con codice pratico che esegui direttamente nel browser, e un tutor IA 24/7 risponde alle tue domande mentre lavori sulla lezione.
Ho bisogno di esperienza per iniziare C# Academy?
Non è richiesta alcuna esperienza precedente. C# Academy su CoddyKit è strutturato per principianti e studenti avanzati, quindi puoi iniziare da qui o dall'inizio e procedere al tuo ritmo. Questa è la lezione 2 di 3.
Quanto tempo richiede la lezione «Matematica generica (panoramica), attributi generici (quando pertinenti)»?
La maggior parte delle lezioni CoddyKit richiede circa 5–10 minuti. Ogni lezione è breve e interattiva, quindi fai progressi costanti e riprendi esattamente da dove hai lasciato su web e app.
Posso scrivere ed eseguire codice in questa lezione C# Academy?
Sì. Ogni lezione C# Academy include un editor di codice integrato, quindi scrivi ed esegui codice reale direttamente nel tuo browser e ricevi feedback istantaneo dall'IA — nessuna configurazione locale necessaria.
Tutte le lezioni di questo corso
- unmanaged, notnull, new() (emulazione in C# 6)
- Matematica generica (panoramica), attributi generici (quando pertinenti)
- Utility generiche riutilizzabili