De gustibus tutta la vita, però io le stringhe cablate nel codice non le sopporto proprio. Una vita intera a tentare di evitarla e poi ti arriva MVVM che, a botte di implementazioni di INotifyPropertyChanged ti fa spuntare come funghi “robe” di questo tipo:
private string emailAddress;
/// <summary>
/// Customer e-mail address
/// </summary>
public string EmailAddress
{
get
{
return this.emailAddress;
}
set
{
this.emailAddress = value;
RaisePropertyChanged("EmailAddress");
}
}
Terribile, nevvero? “Ispirandomi” ad un tip che scrissi per UGIdotNET un paio di anni addietro, mi son detto: perché non usare la stessa tecnica “lambda based” per risolvere il problema una volta per tutte? E quindi:
public static class ReflectionHelper<T>
{
public static string GetPropertyName(Expression<Func<T, object>> subSelector)
{
if (subSelector.Body is MemberExpression)
{
return ((subSelector.Body as MemberExpression).Member as PropertyInfo).Name;
}
else
{
var memberPropertyAccessor = ((subSelector.Body as UnaryExpression).Operand.GetType().GetProperty("Member"));
var memberPropertyValue = memberPropertyAccessor.GetValue((subSelector.Body as UnaryExpression).Operand, null);
var namePropertyAccessor = memberPropertyValue.GetType().GetProperty("Name");
var propertyName = (string)namePropertyAccessor.GetValue(memberPropertyValue, null);
return propertyName;
}
}
}
Che significa poter scrivere il primo snippet così:
private string emailAddress;
/// <summary>
/// Customer e-mail address
/// </summary>
public string EmailAddress
{
get
{
return this.emailAddress;
}
set
{
this.emailAddress = value;
RaisePropertyChanged(
ReflectionHelper<CustomerDetailViewModel>.GetPropertyName(vm => vm.EmailAddress)
);
}
}
Non so voi, ma IMVHO il solo fatto di poter fare refactoring in modo “sicuro” ha giustificato i 10 minuti spesi a scrivere la funziona helper. E’ una lambda: leggere attentamente le avvertenze, usare con cautela.
P.S.: giusto il tempo di portare l’implementazione dallo stato di “funziona” a quello di “fa meno schifo a leggerla” nonché di vedere che i test continuano a dare luce verde, e la infilo in NSK ad imperitura memoria
P.P.S.: Buona anche l’idea di “infilare” la funzione helper in un eventuale classe ViewModelBase, così da evitare la prima parte della invocazione e rendere il codice meno prolisso