ORIENTACAO A OBJETOS - CONCEITO

KERPLUNK 16/09/2013 22:58:34
#428931
Field field = (Field)item.GetCustomAttributes(true).FirstOrDefault(x => x.GetType() == typeof(Field));

field= (Field)item.GetCustomAttributes(true)[0];

A diferença dessas duas linhas:
A primeira, busca o primeiro CustomAttribute que encontrar na propriedade representada por [Ô]item[Ô], em que o tipo seja [Ô]Field[Ô]

A segunda, busca o primeiro CustomeAttribute de field.

Acho que no framework 2.0, você deve antes explicitamente converter a array de CustomAttributes para List:
field = field= (Field)item.GetCustomAttributes(true).ToList().FirstOrDefault(x => x.GetType() == typeof(Field));

Se é que eu entendi sua pergunta
FFCOUTO 17/09/2013 10:22:54
#428943
Kerplunk, você entendeu perfeitamente a minha pergunta. Estive olhando aqui mas o framework 2.0 não tem o método ToList() e nem como usar as expressões lambda.

Existe uma maneira mais prática de pegar esse primeiro atributo sem ter de usar um foreach?

FFCOUTO 17/09/2013 10:38:46
#428947
Já ia me esquecendo. Segue a minha classe singleton para database.


using System;
using System.Text;
using System.Data;
using System.Data.SqlClient;

namespace DBFactory
{
public sealed class Database
{
// propriedade para singleton da classe
private static readonly Database instance = new Database();

// variaveis para conexão singleton
string _connString;

// cria a instância da classe
private Database() { }
// retorna a instância singleton
public static Database GetInstance { get { return instance; } }

// string de conexão
public string ConnectionCommand { get { return _connString; } set { _connString = value; } }

// retornar uma nova conexão; útil para se trabalhar com vários datareaders ao mesmo tempo
public static SqlConnection GetNewConnection()
{
try
{
SqlConnection newConn = new SqlConnection(instance.ConnectionCommand);
newConn.Open();
return newConn;
}
catch
{
return null;
}
}

// retorna a data e hora do servidor (MSSQL Server)
public static DateTime GetDateTime()
{
DateTime dhServ = DateTime.Now;

try
{
// Abre uma nova conexão
SqlConnection connGetDateTime = new SqlConnection(instance.ConnectionCommand);
connGetDateTime.Open();

// Recupera a data e hora atual do servidor SQL Server
string sql = [Ô]SELECT GETDATE() AS hora_atual;[Ô];
SqlCommand cmd = new SqlCommand(sql);
cmd.Connection = connGetDateTime;
cmd.Prepare();

SqlDataReader dr = cmd.ExecuteReader();
if (dr.Read()) { dhServ = Convert.ToDateTime(dr[[Ô]hora_atual[Ô]]); }
dr.Dispose();
dr.Close();

connGetDateTime.Close();
connGetDateTime = null;

// Retorna a data e hora atual do servidor
return dhServ;
}

catch
{
return DateTime.Now;
}
}
}
}


Modo de usar:

// comando de consulta para cliente
sql = [Ô]SELECT * FROM clientes WHERE (id = @id);[Ô];
cmd = new SqlCommand(sql, Database.GetNewConnection());
cmd.Parameters.Add([Ô]@id[Ô], SqlDbType.Int, 4).Value = idCliente;
dr = cmd.ExecuteReader();


Sugestões e críticas serão bem-vindas.
KERPLUNK 17/09/2013 11:17:22
#428949
FFCOUTO,

Seria algo do tipo:

PropertyInfo[] arr = item.GetCustomAttributes(true);
List<PropertyInfo> listPara = new List<PropertyInfo>(arr);

field= (Field)listPara.FirstOrDefault(x => x.GetType() == typeof(Field));
FFCOUTO 17/09/2013 15:46:16
#428967
Kerplunk, desculpe se estou sendo chato, mas o método FirstOrDefault não existe na versão 2.0 do framework. E também não é possível criar métodos de extensão para esta versão.

Eu estou tentando usar delegates mas estou com alguma dificuldade pois sempre mostra os dois erros abaixo:

Citação:

The best overloaded method match for [ô]System.Collections.Generic.List<object>.Find(System.Predicate<object>)[ô] has some invalid arguments

Argument [ô]1[ô]: cannot convert from [ô]anonymous method[ô] to [ô]System.Predicate<object>[ô]



Desde já deixo meus agradecimentos pela ajuda.
KERPLUNK 18/09/2013 11:44:42
#429014
FFCOUTO,

Para o Framework 2.0, use:

Field field = (Field)item.GetCustomAttributes(typeof(Field), true)[0];


O erro que você está tendo é porque no framework 2.0, reflection ainda não estava tão maduro quanto está hoje.
OCELOT 20/09/2013 13:55:43
#429101
Só uma dica, se você está usando o VS.Net 2010 ou superior (talvez com o 2008 também funcione), mesmo que você use o Framework 2.0 você ainda pode usar Linq to Objects e expressões Lambda.

O compilador usado pelo VS.Net suporta estes recursos, só que o framework 2.0 não possui as classes necessárias, então o que precisa ser feito é usar uma biblioteca que adicione as classes necessárias, neste caso existe o LINQBridge que pode ser instalado no projeto direto pelo NuGet.

Com isso você vai poder usar por exemplo o FirstOrDefault e o ToList sem problemas no .Net 2.0
FOXMAN 21/09/2013 21:27:12
#429132
Citação:

:
FOXMAN,

Você pode usar uma decoração de propriedade, que nada mais é que uma classe que herde da classe Attribute:


public class Campo : Attribute
{
public bool Obrigatorio {get;set;}
}


Então na sua classe faça:

public class Carro
{
[Campo(Obrigatorio=true)]
public int x {get; set;}
[Campo(Obrigatorio=false)]
public int y {get;set;}
}



Ao percorrer as propriedades, use o método GetCustomAttribute para buscar o atributo obrigatório:

Carro car = new Carro();
foreach (PropertyInfo item in car.GetType().GetProperties())
{
Campo cmp = (Campo)item.GetCustomAttributes(true).FirstOrDefault(x => x.GetType() == typeof(Campo));
if (cmp.Obrigatorio == true)
Console.WriteLine(string.Format([Ô]Propriedade {0} é VERDADEIRA[Ô], item.Name, cmp.Obrigatorio));
else
Console.WriteLine(string.Format([Ô]Propriedade {0} é FALSA[Ô], item.Name, cmp.Obrigatorio));

}
Console.ReadKey();


Veja que o detalhe importante no exemplo. Dentro do foreach, eu pego o atributo do tipo Campo da propriedade, utilizando um simples FirstOrDefault. Esse é o grande barato da coisa, propriedades, podem ter mais de um atributo, na verdade, podem ter vários, um para cada finalidade. Se tiver alguma dúvida, estamos ae



Kerplunk, maravilha isto já resolveu meu problema.
O engraçado é que eu havia até feito algo parecido, mas declarei um método ao invés de uma propriedade. E sem dúvida seu esclarecimento foi absolutamente exclarecedor.....

Obrigado.
FFCOUTO 23/09/2013 09:40:23
#429151
Citação:

Para o Framework 2.0, use:
Field field = (Field)item.GetCustomAttributes(typeof(Field), true)[0];



Kerplunk, funcionou perfeitamente.

Só uma esclarecimento quanto ao método ConvertDrToEntity postado como exemplo. Ao fazer a carga de uma tabela completa o processamento é demasiado lento, visto que são várias conversões utilizados, portanto, recomendo o uso para leitura de poucos registros. Na tabela que usei como teste, ela tinha apenas 2500 registros e demorou pouco mais 5 minutos para o carregamento completo.

é possível otimizar o uso dessa rotina?

Abraços,
KERPLUNK 25/09/2013 10:15:13
#429231
FFCOUTO,

O framework 2.0, não é muito otimizado para uso de reflection. À partir do 3.5 essas funcionalidades foram muito otimizadas melhorando em muito o desempenho.
Página 11 de 14 [136 registro(s)]
Faça seu login para responder