Arquivos

Archive for setembro \30\UTC 2010

DotNet – Porque usar o “ref” para “ReferenceTypes” ?

Esses dias eu estava conversando com um amigo sobre a necessidade de usar “ref” para passar por referência objetos “ReferenceType” [LINK]. Ele me dizia que não era necessário, e eu dizia que mesmo que não fosse necessário, o ideal era utilizar para aumentar a legibilidade.
Hoje conversando sobre isso na empresa o @tomamais me enviou essa pagina do MSDN [LINK] onde os exemplos 4 e 5 respondem a dúvida.

A RESPOSTA:
Um parâmetro do tipo “reference type” será tratado como passagem por referencia mesmo que não use a palavra reservada “ref”, porem se essa variável for “reinstanciada”, as modificações posteriores não vão refletir fora do método.

class Program
{
    static void Change(int[] arr)
    {
        arr[0] = 888;   // Essa mudança afeta o elemento original.
        arr = new int[5] { -3, -1, -2, -3, -4 };   // Essa mudança é local.
        Console.WriteLine("Dentro do metodo, o primeiro valor é: {0}", arr[0]);
    }

    public static void Main()
    {
        int[] myArray = { 1, 4, 5 }; /// Array de 3 posições
        Console.WriteLine("Na Main, antes da chamada do metodo, o primeiro valor é: {0}", myArray[0]);
        Change(myArray);
        Console.WriteLine("Na Main, depois da chamada do metoro, o primeiro valor é: {0}", myArray[0]);
        Console.Read();
    }
}

Saída no console:
Na Main, antes da chamada do metodo, o primeiro valor é: 1
Dentro do metodo, o primeiro valor é: -3
Na Main, depois da chamada do metoro, o primeiro valor é: 888

É por esse motivo que precisamos usar o “ref”.
Repare que com o uso da palavra reservada, o valor é alterado mesmo reinstanciando a variável.

class Program
{
    static void Change(ref int[] arr)
    {
        arr[0] = 888;   // Essa mudança afeta o elemento original.
        arr = new int[5] { -3, -1, -2, -3, -4 };   // Essa mudança é global.
        Console.WriteLine("Dentro do metodo, o primeiro valor é: {0}", arr[0]);
    }

    public static void Main()
    {
        int[] myArray = { 1, 4, 5 }; /// Array de 3 posições
        Console.WriteLine("Na Main, antes da chamada do metodo, o primeiro valor é: {0}", myArray[0]);
        Change(ref myArray);
        Console.WriteLine("Na Main, depois da chamada do metoro, o primeiro valor é: {0}", myArray[0]);
        Console.Read();
    }
}

Saída no console:
Na Main, antes da chamada do metodo, o primeiro valor é: 1
Dentro do metodo, o primeiro valor é: -3
Na Main, depois da chamada do metoro, o primeiro valor é: -3

CONCLUSÃO:
O uso da palavra reservada “ref” é obrigatório não somente pela legibilidade do código, mas também quando acontece a reinstanciação de uma variável. Quando reinstanciamos a variável dentro método no contexto global, o valor será diferente do desejado.

Categorias.NET Tags:, , , ,

SQL Server – Usando as views de sistema

Olá amigos!

Hoje falarei brevemente sobre um assunto bem interessante no SQL Server que são as views de sistema com informações de schema do banco de dados.

O que são views de sistema?
O Sql Server disponibiliza uma série de views para auxílio na localização de schema de tabelas, views, procedures, entre outras necessidades, facilitando em muito a localização e também a utilização dessas informações

Para quê servem?
Digamos que seja necessário saber em qual tabela temos uma coluna contendo a string “name” em seu nome. Uma forma de resolver isto seria usando a view sysobjects e a view syscolumns, conforme exemplo abaixo:

SELECT * FROM SYSOBJECTS OBJ
INNER JOIN SYSCOLUMNS COL
ON OBJ.ID = COL.ID
WHERE COL.NAME LIKE '%NAME%'

Ótimo, isso funciona perfeitamente, porém existe uma forma mais fácil de fazer isto, usando as views de sistema. Em vez de usar isto, use isto:

SELECT * FROM INFORMATION_SCHEMA.COLUMNS
WHERE COLUMN_NAME LIKE '%name%'

A vantagem mais notável é a sintaxe simplificada ao mesmo tempo uma gama maior de informações retornadas sem necessidade de fazer outros joins com outras views, como é necessário fazer quando usamos as views como sysobjects, syscolumns, etc. Sempre que forem utilizar estas views, é preciso usar o nome qualificado INFORMATION_SCHEMA.nome_da_view.

Abaixo uma lista das principais views do INFORMATION_SCHEMA e seus objetivos:

Nome Descrição
CHECK_CONSTRAINTS Informações sobre as constraints das tabelas
REFERENTIAL_CONSTRAINTS Retorna uma linha para cada FOREIGN KEY no banco selecionado
ROUTINES Todas as funções definidas pelo usuário e stored procedures
COLUMN_PRIVILEGES Colunas com previlégios garantidos para ou pelo usuário atual
ROUTINE_COLUMNS Informações sobre as colunas usadas nas procedures e functions
COLUMNS Informações sobre todas as colunas
SCHEMATA Informações sobre os bancos de dados
CONSTRAINT_COLUMN_USAGE Colunas usadas nas constraints
TABLE_CONSTRAINTS Todas as restrições das tabelas
CONSTRAINT_TABLE_USAGE Tabelas que possuem uma restrição definida
TABLE_PRIVILEGES Tabelas com previlégio garantido para ou pelo usuário atual
TABLES Informações sobre as tabelas
DOMAINS Todos os tipos de dados definidos pelo usuário
VIEW_COLUMN_USAGE Informações sobre colunas utilizadas nas views
KEY_COLUMN_USAGE Colunas restringidas como uma chave
VIEW_TABLE_USAGE Tabelas usadas em uma View
PARAMETERS Todos os parametros para funções definidas pelo usuário e stored procedures
VIEWS Informações sobre as Views

Por hora é isso, façam seus selects e avaliem a necessidade e utilização de cada uma das views citadas.

Referência: http://msdn.microsoft.com/en-us/library/ms186778.aspx

[]‘s

Colunas usadas nas constraints
CategoriasSQL Tags:,

Windows Seven – Menu Iniciar e Barra de Tarefas Clássicos

Essa é uma dica para aquelas pessoas que assim como eu não gostam do menu iniciar e da barra de tarefas do Windows 7.

Menu Iniciar
No Windows 7  não existe uma opcão para deixar o menu iniciar com a mesma aparecia do menu iniciar do Windows XP. Portanto vamos utilizar um programa para isso, eu escolhi o Classic Shell desenvolvido pelo ibeltchev. È um software open source e pode ser encontrado no source forge ( LINK ). A instalação é simples (Next -> Next -> Finish) e a configuração tambem.
No meu caso estou usando o tema classico com somente a opção “Caption” selecionada.

Configurações do Menu Iniciar

Configurações do Menu Iniciar

Barra de Tarefas
Já para a barra de tarefas ficar parecida com a do Windows XP, não precisamos instalar nada. Clique com o botao direito sobre sua area de trebalho, na ultima opção, “Personalizar” e escolha o tema windows classic.
Agora clique com o botao direito sobre a barra de tarefas, “Propriedades”, escolha “Icones pequenos”. Eu ainda escolhi “Nunca agrupar” pois não gosto das janelas agrupadas.
Para ficar ainda mais parecido com o XP, voce pode em configurações avancadas do sistema, desmarcar a seguinte opção nas configurações de “Desempenho”*:

Ccnfigurações da Barra de Tarefas

Configurações da Barra de Tarefas

* Acredito que seja essa a tradução feita pelo windows. Caso alguem use ele em português e possa me corrigir eu seria muito grato.

SQLServer – Ordenando Randomicamente

Uma coisa muito recorrente em nosso dia-a-dia é a necessidade de “ordenarmos” randomicamente uma consulta no SQL. Hoje percebi que isso pode ser um grande problema na vida de muitos. Portanto esse é o assunto do pseudo post (é muito curto para ser um post).
Vamos direto ao código:

SELECT * FROM tabela ORDER BY NEWID()

Complexo não? Mas tenho certeza que vai ajudar muitos.

CategoriasSQL Tags:

MVC – Sitemap simples e eficiente

No blog www.rafaelalmeida.net, postei a pouco tempo sobre sitemaps com o asp.net MVC. Ficou bem bacana então resolvi replicar aqui. Vale lembrar que a solução inicial foi do Joel Abrahamssom e minha solução apresentada abaixo difere apenas em alguns pontos com por exemplo a maneira de criar os itens que vão ser exibidos.
O código é bem simples e intuitivo, caso alguém ainda tenha dúvida deixa um comentário.

namespace RafaelAlmeida.Controllers
{
    public class SitemapController : Controller
    {
        //
        // GET: /Sitemap/
        public XmlSitemapResult Index()
        {
	    /// Monta o site map
            var itens = new SitemapItensCollection();
            AddEntries(ref itens);

            return new XmlSitemapResult(itens);
        }

        private void AddEntries(ref SitemapItensCollection itens)
        {
	    /// Identifica os posts que vão para o sitemap
            var repository = new Models.BlogRepository();
            foreach (var post in repository.getPosts())
            {
                itens.Add(new SitemapItem(@"http://www.rafaelalmeida.net/post/" + post.name) { ChangeFrequency= ChangeFrequency.Weekly, Priority=1, LastModified = post.date});
            }
        }
    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    public class XmlSitemapResult : ActionResult
    {
	/// Itens
        private readonly SitemapItensCollection _items;

	/// Construtor
        public XmlSitemapResult(SitemapItensCollection items)
        {
            _items = items;
        }

	/// Gera o xml com o sitemap
        public override void ExecuteResult(ControllerContext context)
        {
            context.HttpContext.Response.ContentType = "application/rss+xml";
            context.HttpContext.Response.Flush();

            var ser = new XmlSerializer(typeof(SitemapItensCollection));
            ser.Serialize(context.HttpContext.Response.Output, _items);
        }
    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    /// Coloca os namespaces
    [XmlType(Namespace = "http://www.google.com/schemas/sitemap/0.84", TypeName = "urlset")]
    [XmlRootAttribute(Namespace = "http://www.google.com/schemas/sitemap/0.84", ElementName = "urlset", IsNullable = false)]
    public class SitemapItensCollection: List<SitemapItem>
    {

    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    [XmlTypeAttribute(TypeName = "url")]
    public class SitemapItem : ISitemapItem
    {
	/// Construtor
        public SitemapItem()
        {

        }

	/// Construtor
        public SitemapItem(string url)
        {
            Url = url;
        }

	/// Url do Post
        [XmlElementAttribute( DataType = "anyURI", ElementName= "loc")]
        public string Url { get; set; }

	/// Data de modificação
        [XmlElementAttribute(DataType = "date", ElementName = "lastmod")]
        public DateTime? LastModified { get; set; }

	/// Frequencia de atualização
        [XmlElementAttribute( ElementName = "changefreq")]
        public ChangeFrequency? ChangeFrequency { get; set; }

	/// Prioridade
        [XmlElementAttribute(ElementName = "priority")]
        public float? Priority { get; set; }
    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    /// Tipos de Frequencia
    public enum ChangeFrequency
    {
        Always,
        Hourly,
        Daily,
        Weekly,
        Monthly,
        Yearly,
        Never
    }
}

namespace net.rafaelalmeida.XmlSitemap
{
    /// Interface de item do sitemap
    public interface ISitemapItem
    {
	/// URL
        string Url { get; }

	/// Data de modificação
        DateTime? LastModified { get; }

	/// Frequencia de atualização
        ChangeFrequency? ChangeFrequency { get; }

	/// Prioridade
        float? Priority { get; }
    }
}

Um exemplo dele funcionando é o sitemap do meu blog pessoal http://rafaelalmeida.net/sitemap/index.

Categorias.NET, asp.net, MVC, SEO, SiteMap, XML Tags:, , , ,

SQLServer – Zerando valor da coluna Identity

Simples mas útil.
Se você estiver usando uma coluna definida como “Identity” em uma tabela SQL Server, você pode definir qual o próximo valor a ser inserido nesta coluna. Por exemplo, definir que o número da sua coluna ID seja definido como 500 ao invés de 1, que seria o padrão. Abaixo alguns exemplos de como fazer isso e outras utilizações:

Para saber qual será a próxima numeração a ser inserida na coluna identificadora:

DBCC CHECKIDENT ('tablename', NORESEED)

Se quiser então saber o valor do próximo ID na tabela “usuarios”, pode-se usar este comando:

DBCC CHECKIDENT (usuarios, NORESEED)

Para definir o próximo valor da sua coluna ID para 1000, use o seguinte:

DBCC CHECKIDENT (usuarios, RESEED, 999)

Note que o próximo valor será 1000, pois é o valor informado no comando + 1.

Um último detalhe é que você pode envolver o nome da tabela com aspas simples, ou os colchetes quando estiver falando em situações especiais como nome de tabela com espaços (o que eu não gosto) ou caminho completo da tabela:

DBCC CHECKIDENT ( 'seubancodedados.dbo.usuarios', RESEED, 999)

[]‘s e até a próxima!

CategoriasSQL Tags:

C# – Obtendo os valores de todas as propriedades de um objeto

Acho que deu para perceber que o pessoal deste blog gosta de C#, certo? Bom, segue uma contribuição, antes que me expulsem daqui. ;)

Tinha esquecido desse snippet. Com certeza ajuda, principalmente na depuração de aplicações.

Quando precisar saber os valores de todas as propriedades de um objeto, ao invés de sair destacando uma por uma, a rotina abaixo devolve os valores das propriedades de um determinado objeto, passado por parâmetro:

public static Dictionary<string, object> getPropertyValues(object o)
{
    Dictionary<string, object> propertyValues = new Dictionary<string, object>();
    Type ObjectType = o.GetType();
    System.Reflection.PropertyInfo[] properties = ObjectType.GetProperties();
    foreach (System.Reflection.PropertyInfo property in properties)
    {
        propertyValues.Add(property.Name, property.GetValue(o, null));
    }
    return propertyValues;
}

O código retorna um Dictionary, onde a string é o nome da propriedade e o object, seu valor. Inevitavelmente, é preciso o uso de Reflection para obter tais informações, o que provavelmente o leitor já esperava, certo? Daí para frente é só utilizar como bem entender.

O macete também é muito bom quando se quer “clonar” um objeto, podendo inclusive adicionar regras específicas para o contexto.

Bom proveito!

Categorias.NET Tags:,

IronRuby – Integração com .Net

Hoje vou falar um pouco sobre IronRuby. Não sou um expert, mas comecei a brincar com o IronRuby, e percebi que ele é mais uma ferramenta pra guardar em nossa caixa de ferramentas.

Em alguns casos queremos precisamos de uma linguagem dinâmica para realizar tarefas complicadas de maneira muito mais facil. Imagine por exemplo que você quer permitir que o cliente defina um script para calculo do frete, normalmente se usaria um vbscript. Mas porque não utilizar uma linguagem dinâmica como o ruby? Alguns, como eu, devem estar achando que integrar uma linguagem como o ruby ao .net deve ser muito complicado, se você é um desses é porque não conhece o IronRuby (ou IronPyton, teoricamente os dois são muito parecidos).

No exemplo que colocarei para download, mostro como integrar o IronRuby com C#, para isso crio uma Interface simples ICalc e implemento ela em duas classes do ruby. depois executo as duas “calculadoras” que implementei (“somadora” e “multiplicadora”).

Segue o exemplo do codigo:

public void CriaCalculadora
{
var runtime = Ruby.CreateRuntime();
var engine = runtime.GetEngine("rb");

var paths = new List<string>();
paths.Add(@"E:\Workspace\RafaelAlmeida.net\Trunk\Exemplos\IronRuby\Calculators.Console\bin\Release");
engine.SetSearchPaths(paths);

// Cria calculadora que sabe multiplicar
engine.ExecuteFile("Pessoa.rb");
var rubyClass = engine.Runtime.Globals.GetVariable("Multiplicadora");
var calculator = (ICalc)engine.Operations.CreateInstance(rubyClass);

// Calcula
var result = calculator.calculate(A, B);

// Imprime resultado
System.Console.WriteLine(string.Format("A * B = {0}", result));

// Cria calculadora que sabe somar
rubyClass = engine.Runtime.Globals.GetVariable("Somadora");
calculator = (ICalc)engine.Operations.CreateInstance(rubyClass);

// Calcula
result = calculator.calculate(A, B);

// Imprime resultado
System.Console.WriteLine(string.Format("A + B = {0}", result));
}

Simples não é? Se você quiser ver o exemplo completo, faça o download [ Aqui ]

RegEx – Como Remover Tags HTML de uma string

Mais uma vez quero demonstrar como um regex, utilizado corretamente, pode ser poderoso. Imagine uma string qualquer onde você tenha tags HTML dentro:

“<p>Hi, <br/> “text .</strong>“</p> bad html </ul>will be removed too.”

Agora imagine que você tenha que remover todas as tags HTML dessa string.
Já vi muita gente fazer um replace nas tags HTML (uma por uma) e substituilas pela string vazia.

Realmente é uma saida, mas não é a mais inteligente, funciona até que alguem coloque uma tag que você não tenha previsto. Uma maneira mais eficiente de fazer isso, é usando um Regex. vamos ao exemplo:

static void Main(string[] args)
{
// Some String
const string text = "<p>Hi,  <br/> “Walking on water and developing software from a  specification are easy if both are <strong>frozen.</strong>“  - Edward V. Berard</p> here some bad html </ul>will be  removed too.";

// Write the string with the html tags
Console.WriteLine(text);

// Write the string without the html tags
Console.WriteLine(RemoveHtmlTags(text));

Console.ReadLine();
}

private static string RemoveHtmlTags(string htmlString)
{

// Regex to find all the html tags
const string pattern = @"<(.|\n)*?>";

// Return the string without html tags
return Regex.Replace(htmlString, pattern, string.Empty);

}

Achei que podia ajudar algumas pessoas, então resolvi postar.

Creditos para http://aliraza.wordpress.com/, foi la que achei a primeira versão.

Dicas – Atalhos rápidos (demais) para seus aplicativos

A dica é do Rafael Almeida, mas acho que ele não vai se importar em me emprestá-la para colocar aqui, certo?

Uma forma rápida, mas pouco usual de criar atalhos no Windows é a citada a seguir:

  • Criaremos um atalho para o Bloco de Notas (famoso notepad) como exemplo
  • Crie o atalho que deseja e coloque-o no Desktop
  • Para facilitar, clique com o botão direito do mouse sobre o ícone onde ele estiver, Enviar para->Área de trabalho (criar atalho)
  • Nomeie-o para algo simples, como por exemplo, a letra “n”
  • Em seguida, abra a pasta padrão do sistema Windows (C:\WINDOWS no Windows XP em diante)
  • Coloque esse atalho lá

Agora, para executar o Bloco de Notas, basta ir ao Iniciar->Executar (ou se preferir, usar o atalho Windows + R) e na caixa de diálogo Executar, digite o nome do nosso atalho, no caso, “n” (sem aspas) e clique em OK.

Voilá! Nosso atalho funciona! Imagine agora as possibilidades que você pode criar para seus atalhos? Bom, o computador é seu, portanto, divirta-se!

Cuidados

Para os menos familiarizados, é preciso tomar extremo cuidado com o conteúdo da pasta C:\WINDOWS. O conteúdo refere-se a instalação do Windows e seus componentes. Portanto, para os que querem arriscar, não há muito problema em criar arquivos nesta pasta. Porém, evite ao máximo alterar qualquer outro que já exista dentro dela.

Bom proveito!

A dica é do Rafael Almeida, mas acho que ele não vai se importar em me emprestá-la para colocar aqui, certo?

Uma forma rápida, mas pouco usual de criar atalhos no Windows é a citada a seguir:

Criaremos um atalho para o Bloco de Notas (famoso notepad) como exemplo
Crie o atalho que deseja e coloque-o no Desktop
Para facilitar, clique com o botão direito do mouse sobre o ícone onde ele estiver, Enviar para->Área de trabalho (criar

atalho)
Nomeie-o para algo simples, como por exemplo, a letra “n”
Em seguida, abra a pasta padrão do sistema Windows (C:\WINDOWS no Windows XP em diante)
Coloque esse atalho lá

Agora, para executar o Bloco de Notas, basta ir ao Iniciar->Executar (ou se preferir, usar o atalho Windows + R) e na

caixa de diálogo Executar, digite o nome do nosso atalho, no caso, “n” (sem aspas) e clique em OK.

Voilá! Nosso atalho funciona! Imagine agora as possibilidades que você pode criar para seus atalhos? Bom, o computador é

seu, portanto, divirta-se!

Cuidados

Para os menos familiarizados, é preciso tomar extremo cuidado com o conteúdo da pasta C:\WINDOWS. O conteúdo refere-se a instalação do Windows e seus componentes. Portanto, para os que querem arriscar, não há muito problema em criar arquivos nesta pasta. Porém, evite ao máximo alterar qualquer outro que já exista dentro dela.

Bom proveito!

CategoriasWindows Tags:,
Seguir

Obtenha todo post novo entregue na sua caixa de entrada.