<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet href="http://feeds.feedburner.com/~d/styles/rss2full.xsl" type="text/xsl" media="screen"?><?xml-stylesheet href="http://feeds.feedburner.com/~d/styles/itemcontent.css" type="text/css" media="screen"?><!-- generator="wordpress/2.3.1" --><rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>Log4Dev</title>
	<link>http://log4dev.com</link>
	<description>Nós temos algo a dizer sobre tecnologia</description>
	<pubDate>Sat, 29 Nov 2008 20:47:44 +0000</pubDate>
	<generator>http://wordpress.org/?v=2.3.1</generator>
	<language>en</language>
			<image><link>http://log4dev.com.br</link><url>http://log4dev.com/wp-includes/images/logo_laranja.gif</url><title>Log4Dev - RSS</title></image><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" href="http://feeds.feedburner.com/log4dev/xml" type="application/rss+xml" /><feedburner:feedFlare href="http://add.my.yahoo.com/rss?url=http%3A%2F%2Ffeeds.feedburner.com%2Flog4dev%2Fxml" src="http://us.i1.yimg.com/us.yimg.com/i/us/my/addtomyyahoo4.gif">Subscribe with My Yahoo!</feedburner:feedFlare><feedburner:feedFlare href="http://www.newsgator.com/ngs/subscriber/subext.aspx?url=http%3A%2F%2Ffeeds.feedburner.com%2Flog4dev%2Fxml" src="http://www.newsgator.com/images/ngsub1.gif">Subscribe with NewsGator</feedburner:feedFlare><feedburner:feedFlare href="http://feeds.my.aol.com/add.jsp?url=http%3A%2F%2Ffeeds.feedburner.com%2Flog4dev%2Fxml" src="http://o.aolcdn.com/favorites.my.aol.com/webmaster/ffclient/webroot/locale/en-US/images/myAOLButtonSmall.gif">Subscribe with My AOL</feedburner:feedFlare><feedburner:feedFlare href="http://www.bloglines.com/sub/http://feeds.feedburner.com/log4dev/xml" src="http://www.bloglines.com/images/sub_modern11.gif">Subscribe with Bloglines</feedburner:feedFlare><feedburner:feedFlare href="http://www.netvibes.com/subscribe.php?url=http%3A%2F%2Ffeeds.feedburner.com%2Flog4dev%2Fxml" src="http://www.netvibes.com/img/add2netvibes.gif">Subscribe with Netvibes</feedburner:feedFlare><feedburner:feedFlare href="http://fusion.google.com/add?feedurl=http%3A%2F%2Ffeeds.feedburner.com%2Flog4dev%2Fxml" src="http://buttons.googlesyndication.com/fusion/add.gif">Subscribe with Google</feedburner:feedFlare><feedburner:feedFlare href="http://www.pageflakes.com/subscribe.aspx?url=http%3A%2F%2Ffeeds.feedburner.com%2Flog4dev%2Fxml" src="http://www.pageflakes.com/ImageFile.ashx?instanceId=Static_4&amp;fileName=ATP_blu_91x17.gif">Subscribe with Pageflakes</feedburner:feedFlare><item><title>Links for 2008-11-30 [del.icio.us]</title><link>http://feeds.feedburner.com/~r/log4dev/xml/~3/470963550/log4dev</link><pubDate>Mon, 01 Dec 2008 00:00:00 -0600</pubDate><guid isPermaLink="false">http://del.icio.us/log4dev#2008-11-30</guid><content:encoded><![CDATA[<ul>
<li><a href="http://www.ibm.com/developerworks/xml/library/x-atom10.html">An overview of the Atom 1.0 Syndication Format</a></li>
</ul><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/470963550" height="1" width="1"/>]]></content:encoded><description>&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.ibm.com/developerworks/xml/library/x-atom10.html"&gt;An overview of the Atom 1.0 Syndication Format&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;</description><feedburner:origLink>http://del.icio.us/log4dev#2008-11-30</feedburner:origLink></item><item><title>Links for 2008-11-29 [del.icio.us]</title><link>http://feeds.feedburner.com/~r/log4dev/xml/~3/469985165/log4dev</link><pubDate>Sun, 30 Nov 2008 00:00:00 -0600</pubDate><guid isPermaLink="false">http://del.icio.us/log4dev#2008-11-29</guid><content:encoded><![CDATA[<ul>
<li><a href="http://www.paulgraham.com/artistsship.html">The Other Half of &quot;Artists Ship&quot;</a></li>
</ul><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/469985165" height="1" width="1"/>]]></content:encoded><description>&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.paulgraham.com/artistsship.html"&gt;The Other Half of &amp;quot;Artists Ship&amp;quot;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;</description><feedburner:origLink>http://del.icio.us/log4dev#2008-11-29</feedburner:origLink></item><item>
		<title>Sobre controle de versão distribuído</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/469634817/</link>
		<comments>http://log4dev.com/2008/11/29/sobre-controle-de-versao-distribuido/#comments</comments>
		<pubDate>Sat, 29 Nov 2008 20:47:44 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Desenvolvimento]]></category>

		<category><![CDATA[Ferramentas]]></category>

		<category><![CDATA[Mercurial]]></category>

		<category><![CDATA[SVN]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/11/29/sobre-controle-de-versao-distribuido/</guid>
		<description><![CDATA[Um dos grandes desafios da vida de um profissional de tecnologia é de se manter atualizado em relação às novidades e rumos do mundo da computação. A quantidade de fontes de informação é &#8220;gigantescamente&#8221; enorme, e é necessário ter um bom filtro interno para conseguir separar o joio do trigo, extrair aquilo que nos interessa [...]]]></description>
			<content:encoded><![CDATA[<p>Um dos grandes desafios da vida de um profissional de tecnologia é de se manter atualizado em relação às novidades e rumos do mundo da computação. A quantidade de fontes de informação é &#8220;gigantescamente&#8221; enorme, e é necessário ter um bom filtro interno para conseguir separar o joio do trigo, extrair aquilo que nos interessa e manter a sanidade mental.</p>
<p>O meu processo de absorção de novidades é por etapas. Em geral eu leio ou ouço falar sobre algo novo, e guardo em um lugar remoto do meu cérebro. Muitas vezes, eu conto com a colaboração do meu colega de blog e junkreader profissional, senhor Lullis, Raphael Lullis. Com o passar do tempo, algumas das novidades vão sendo eliminadas, e algumas poucas são promovidas para a próxima fase. Após alguns paredões, eu acabo resolvendo aprender as que sobreviveram. Normalmente, as tecnologias que ficam são aquelas que por algum motivo se tornam necessárias no meu cotidiano.</p>
<p>Foi assim com django, com Ajax, com python. E agora, sistemas de controle de versão distribuídos (<a href="http://www.selenic.com/mercurial/wiki/" onclick="javascript:urchinTracker('/outbound/article/www.selenic.com');">Mercurial</a> ou <a href="http://git.or.cz/" onclick="javascript:urchinTracker('/outbound/article/git.or.cz');">Git</a>) estão próximos da fase final de aprovação. Pra variar, o Raphael é parcialmente culpado por isso. Ele tem um lado Cuco: a cada 2 dias reaparece e martela sobre um tema. E vira e mexe ele vem me falar das maravilhas do uso de um Mercurial da vida. No começo achei um tanto quanto viajado. Mas agora, me parece extremamente útil.</p>
<p>Aliás, quero aproveitar antes para falar sobre o conceito de repositório. Pelo fato de um sistema distribuído não ter o conceito de repositório central, algumas pessoas acham que a coisa tende ao caos. Eu pensava assim. O grande lance é que ao contrário de um sistema como SVN onde existe um repositório e as pessoas baixam working copies, num sistema distribuído cada máquina é um repositório.</p>
<p>Dois elementos me parecem muito atraentes nestes sistemas, e me fazem falta atualmente: a <strong>possibilidade de ter um repositório local</strong>, e a <strong>possibilidade de compartilhar seu trabalho com outras pessoas sem a necessidade de passar por um repositório central</strong>.</p>
<p>O primeiro elemento é algo que pode ser parcialmente resolvido por bons IDEs como o Eclipse, que oferece um histórico local. Mas históricos locais são ótimos para resolver problemas em arquivos separados. A coisa se torna mais complicada quando queremos voltar conjuntos de arquivos. Para isso, já nos acostumamos a ter uma ferramenta de controle de versão, que permite comitar e comentar checkpoints de trabalhos. O fato é que quando se trabalha em grupo, o ideal é que os commits no repositório central sejam completos. Mas muitas vezes, uma implementação pode ser quebrada em várias sub-tarefas que não podem/devem ser compartilhadas com a equipe, e ter um histórico apurado destas subtarefas pode ser muito útil. Que jogue a primeira pedra aquele que nunca passou horas e horas escrevendo código,  e que no final das contas teve que voltar tudo atrás usando um revert.</p>
<p>O segundo elemento é algo que pode resolver vários problemas. Um deles é  permitir criar níveis de repositórios: um de desenvolvimento, um de testes, um de produção. Todos com histórico, tags, versões e afins. Trabalhei num projeto onde muitas vezes o repositório ficava instável, e era um deusnosacuda para montar uma versão para cliente.</p>
<p>Outra característica interessante é permitir que subgrupos dentro de uma equipe de desenvolvimento possam compartilhar código sem a necessidade de ter que criar um branch ou, pior, zipar o diretório e mandar por email. Tudo se resolveria com um merge simples entre pares.</p>
<p>Eu sei perfeitamente que para que tudo isso funcione, é necessário uma readaptação da equipe à nova ferramenta e sobretudo, ao novo modus operandi. Mas parto do pressuposto que as pessoas que trabalham comigo são espertas o suficiente para isso. E pensando bem, se fomos capazes de aprender a trabalhar com sistema de controle de versões, porque não seríamos capazes de aprender a trabalhar com um sistema distríbuido?</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=RYVPN"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=RYVPN" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=nu4dN"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=nu4dN" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/469634817" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/11/29/sobre-controle-de-versao-distribuido/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/11/29/sobre-controle-de-versao-distribuido/</feedburner:origLink></item>
		<item><title>Links for 2008-11-17 [del.icio.us]</title><link>http://feeds.feedburner.com/~r/log4dev/xml/~3/456820136/log4dev</link><pubDate>Tue, 18 Nov 2008 00:00:00 -0600</pubDate><guid isPermaLink="false">http://del.icio.us/log4dev#2008-11-17</guid><content:encoded><![CDATA[<ul>
<li><a href="http://www.lshift.net/blog/2008/11/14/tracing-python-memory-leaks">LShift Ltd. &raquo; Tracing Python memory leaks</a><br/>
It’s not so easy for a Python application to leak memory. Usually there are three scenarios:

   1. some low level C library is leaking
   2. your Python code have global lists or dicts that grow over time, and you forgot to remove the objects after use
   3. there are some reference cycles in your app</li>
<li><a href="http://www.amk.ca/python/howto/unicode">Python Unicode HOWTO</a></li>
</ul><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/456820136" height="1" width="1"/>]]></content:encoded><description>&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.lshift.net/blog/2008/11/14/tracing-python-memory-leaks"&gt;LShift Ltd. &amp;raquo; Tracing Python memory leaks&lt;/a&gt;&lt;br/&gt;
It’s not so easy for a Python application to leak memory. Usually there are three scenarios:

   1. some low level C library is leaking
   2. your Python code have global lists or dicts that grow over time, and you forgot to remove the objects after use
   3. there are some reference cycles in your app&lt;/li&gt;
&lt;li&gt;&lt;a href="http://www.amk.ca/python/howto/unicode"&gt;Python Unicode HOWTO&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;</description><feedburner:origLink>http://del.icio.us/log4dev#2008-11-17</feedburner:origLink></item><item>
		<title>Novidades do Google</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/451139827/</link>
		<comments>http://log4dev.com/2008/11/12/novidades-do-google/#comments</comments>
		<pubDate>Wed, 12 Nov 2008 21:37:26 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Google]]></category>

		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/11/12/novidades-do-google/</guid>
		<description><![CDATA[Duas notícias interessantes relacionadas ao Google.
A primeira, noticiada pelo Blog oficial do GMail é para aficcionados por comunicação instantânea (eu por exemplo):  será possível fazer chat de áudio e vídeo dentro da interface web do sistema de emails. Basta instalar um plugin, e se divertir. Se funcionar corretamente, irá transformar o GMail numa central de [...]]]></description>
			<content:encoded><![CDATA[<p>Duas notícias interessantes relacionadas ao Google.</p>
<p>A primeira, <a href="http://gmailblog.blogspot.com/2008/11/say-hello-to-gmail-voice-and-video-chat.html" onclick="javascript:urchinTracker('/outbound/article/gmailblog.blogspot.com');">noticiada pelo Blog oficial do GMail</a> é para aficcionados por comunicação instantânea (eu por exemplo):  será possível fazer chat de áudio e vídeo dentro da interface web do sistema de emails. Basta instalar um plugin, e se divertir. Se funcionar corretamente, irá transformar o GMail numa central de comunicação completa.</p>
<p>A segunda notícia é mais intrigante. O <a href="http://www.google.org" onclick="javascript:urchinTracker('/outbound/article/www.google.org');">Google.org</a>, braço filantrópico do Google, está lançando uma <a href="http://www.google.org/flutrends/" onclick="javascript:urchinTracker('/outbound/article/www.google.org');">ferramenta de detecção de epidemias de gripe nos Estados Unidos</a>. O mecanismo de detecção é de uma simplicidade incrível, e ao mesmo tempo um tanto quanto preocupante: o próprio sistema de buscas da empresa. A premissa básica é que atualmente, quando pessoas sentem sintomas de alguma doença, procuram na Internet informações a respeito dos sintomas. Como hoje em dia, busca na Internet é sinônimo de busca no Google, então &#8220;basta&#8221; eles analisarem e georeferenciarem a ocorrência de termos específicos (coisa que a ferramenta Google Trends faz de graça),  para obter uma boa estimativa de regiões onde poderiam estar começando epidemias. Nada de registros médicos, apenas buscas simples na interface do Google.</p>
<p>Expandindo a idéia, como hoje em dia a fonte básica de pesquisas é a internet, e boa parte dela passa pelos servidores do Larry e do Sergei, e que ferramentas como o Google Analytics mostraram que a questão do georeferenciamento de IPs já foi resolvida, então podemos assumir que eles se tornaram a maior empresas de análises estatísticas do mundo. Que aliás eles utilizaram para analisar buscas feitas durante a campanha eleitoral.</p>
<p>Big Brother?</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=YvZlN"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=YvZlN" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=DZ0UN"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=DZ0UN" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/451139827" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/11/12/novidades-do-google/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/11/12/novidades-do-google/</feedburner:origLink></item>
		<item>
		<title>Speedy agora REALMENTE não pode mais</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/445389225/</link>
		<comments>http://log4dev.com/2008/11/07/speedy-agora-realmente-nao-pode-mais/#comments</comments>
		<pubDate>Fri, 07 Nov 2008 11:28:32 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Speedy]]></category>

		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/11/07/speedy-agora-realmente-nao-pode-mais/</guid>
		<description><![CDATA[Há um tempo atrás, eu comentei da possibilidade do Speedy &#8220;não poder mais&#8221; oferecer autenticação sem a necessidade de provedor externo. Pois é: o dia chegou!  A partir de hoje, dia 07/11/2008, a Telefônica, por decisão judicial, não pode mais oferecer autenticação através do usuário internet@speedy.com.br, e os usuários terão que contratar provedor externo.
Novamente, destaquei [...]]]></description>
			<content:encoded><![CDATA[<p>Há um tempo atrás, eu comentei da possibilidade do Speedy <strong>&#8220;não poder mais&#8221;</strong> oferecer autenticação sem a necessidade de provedor externo. Pois é: o dia chegou!  A partir de hoje, dia <strong>07/11/2008</strong>, a Telefônica, <strong>por decisão judicial</strong>, não pode mais oferecer autenticação através do usuário <strong>internet@speedy.com.br</strong>, e os usuários terão que contratar provedor externo.</p>
<p>Novamente, destaquei o &#8220;por decisão judicial&#8221;, porque acho o cúmulo do absurdo o comunicado da empresa deixar  a entender que a culpa é da Justiça, eque está fazendo isso contra a sua vontade. Afinal todos sabemos que o inicio disso tudo foi uma liminar de um juiz de Baurú proibindo a Telfônica de exigir o provedor.</p>
<p>Ridículo.</p>
<p>A boa notícia é que o <a href="http://www.speedyvantagens.com.br/provedores/" onclick="javascript:urchinTracker('/outbound/article/www.speedyvantagens.com.br');">site deles</a> oferece uma lista de provedores com &#8220;preços e promoções&#8221; especiais&#8230;..</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=da4gN"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=da4gN" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=XS4yN"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=XS4yN" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/445389225" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/11/07/speedy-agora-realmente-nao-pode-mais/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/11/07/speedy-agora-realmente-nao-pode-mais/</feedburner:origLink></item>
		<item><title>Links for 2008-11-04 [del.icio.us]</title><link>http://feeds.feedburner.com/~r/log4dev/xml/~3/442887720/log4dev</link><pubDate>Wed, 05 Nov 2008 00:00:00 -0600</pubDate><guid isPermaLink="false">http://del.icio.us/log4dev#2008-11-04</guid><content:encoded><![CDATA[<ul>
<li><a href="http://google-code-updates.blogspot.com/2008/03/introducing-google-visualization-api.html">Google Code Blog: Introducing the Google Visualization API</a><br/>
we&#039;re please to introduce the Google Visualization API, which is designed to make it easier for a wide audience to make use of advanced visualization technology, and do so in a way that makes it quick and easy to integrate with new visualizations.</li>
<li><a href="http://googleblog.blogspot.com/2008/11/visualizing-data-in-cloud.html">Official Google Blog: Visualizing data in the cloud</a><br/>
Today, we are expanding the capabilities of the Google Visualization API by enabling developers to display data from any data source connected to the web (any database, Excel spreadsheet, etc.), not just from Google Spreadsheets. From pivot tables and heat graphs to motion charts and timelines, the Google Visualization Gallery holds a growing set of 40+ visualizations that appeal to a multitude of businesses.</li>
<li><a href="http://code.google.com/apis/visualization/">Google Visualization API - Google Code</a><br/>
The Google Visualization API lets you access multiple sources of structured data that you can display, choosing from a large selection of visualizations. Google Visualization API enables you to expose your own data, stored on any data-store that is connected to the web, as a Visualization compliant datasource. Thus you can create reports and dashboards as well as analyze and display your data through the wealth of available visualization applications. The Google Visualization API also provides a platform that can be used to create, share and reuse visualizations written by the developer community at large.</li>
</ul><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/442887720" height="1" width="1"/>]]></content:encoded><description>&lt;ul&gt;
&lt;li&gt;&lt;a href="http://google-code-updates.blogspot.com/2008/03/introducing-google-visualization-api.html"&gt;Google Code Blog: Introducing the Google Visualization API&lt;/a&gt;&lt;br/&gt;
we&amp;#039;re please to introduce the Google Visualization API, which is designed to make it easier for a wide audience to make use of advanced visualization technology, and do so in a way that makes it quick and easy to integrate with new visualizations.&lt;/li&gt;
&lt;li&gt;&lt;a href="http://googleblog.blogspot.com/2008/11/visualizing-data-in-cloud.html"&gt;Official Google Blog: Visualizing data in the cloud&lt;/a&gt;&lt;br/&gt;
Today, we are expanding the capabilities of the Google Visualization API by enabling developers to display data from any data source connected to the web (any database, Excel spreadsheet, etc.), not just from Google Spreadsheets. From pivot tables and heat graphs to motion charts and timelines, the Google Visualization Gallery holds a growing set of 40+ visualizations that appeal to a multitude of businesses.&lt;/li&gt;
&lt;li&gt;&lt;a href="http://code.google.com/apis/visualization/"&gt;Google Visualization API - Google Code&lt;/a&gt;&lt;br/&gt;
The Google Visualization API lets you access multiple sources of structured data that you can display, choosing from a large selection of visualizations. Google Visualization API enables you to expose your own data, stored on any data-store that is connected to the web, as a Visualization compliant datasource. Thus you can create reports and dashboards as well as analyze and display your data through the wealth of available visualization applications. The Google Visualization API also provides a platform that can be used to create, share and reuse visualizations written by the developer community at large.&lt;/li&gt;
&lt;/ul&gt;</description><feedburner:origLink>http://del.icio.us/log4dev#2008-11-04</feedburner:origLink></item><item>
		<title>Micro introdução sobre orientação a aspectos (AspectJ)</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/442663995/</link>
		<comments>http://log4dev.com/2008/11/04/micro-introducao-sobre-orientacao-a-aspectos-aspectj/#comments</comments>
		<pubDate>Wed, 05 Nov 2008 00:28:55 +0000</pubDate>
		<dc:creator>Thiago</dc:creator>
		
		<category><![CDATA[Desenvolvimento]]></category>

		<category><![CDATA[Design]]></category>

		<category><![CDATA[Ferramentas]]></category>

		<category><![CDATA[Pesquisa]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/11/04/micro-introducao-sobre-orientacao-a-aspectos-aspectj/</guid>
		<description><![CDATA[Eu estava pensando em escrever sobre algumas coisas que têm me interessado ultimamente e que têm alguma relação com o post sobre vazamento de memoria em Java, mas eu percebi que não teria como, sem fazer uma pequena introdução sobre programação orientada a aspectos (aspect oriented programming, AOP). A gente já discutiu um pouco sobre [...]]]></description>
			<content:encoded><![CDATA[<p>Eu estava pensando em escrever sobre algumas coisas que têm me interessado ultimamente e que têm alguma relação com o <a href="http://log4dev.com/2008/10/25/vazamento-de-memoria-em-java/" >post sobre vazamento de memoria em Java</a>, mas eu percebi que não teria como, sem fazer uma pequena introdução sobre programação orientada a aspectos (aspect oriented programming, AOP). A gente já discutiu um pouco sobre isso no post sobre <a href="http://log4dev.com/2008/04/24/poor-mans-profiler-decorators-em-python/" >decorators em python</a>, mas não fizemos nada mais introdutório (se você já tem uma noção do assunto, provavelmente não vai achar esse artigo muito útil). Então nesse post eu vou falar sobre alguns conceitos de <a href="http://aosd.net" onclick="javascript:urchinTracker('/outbound/article/aosd.net');">desenvolvimento orientado a aspectos</a>(AOSD), mas com ênfase descarada em AOP na forma como implementada em <a href="http://www.eclipse.org/aspectj/" onclick="javascript:urchinTracker('/outbound/article/www.eclipse.org');">AspectJ</a>. Eu não pretendo cobrir em profundidade o assunto, pretendo somente dar uma idéia da motivação e discutir alguns pontos sobre o paradigma. Além disso, eu vou usar na maioria a terminologia em inglês, pois eu acho estranho traduzir termos tecnológicos. Se alguem tiver interessado em termos em português, o pessoal do workshop em AOP (WASP&#8217;04) fez um <a href="http://twiki.dcc.ufba.br/bin/view/WASP04/Termos" onclick="javascript:urchinTracker('/outbound/article/twiki.dcc.ufba.br');">catálogo de termos</a>.</p>
<p><strong>Motivação e Exemplo</strong></p>
<p>No meu ponto de vista, AOSD não é algo que veio revolucionar o desenvolvimento de software, mas sim um avanço incremental do paradigma de orientação a objetos (OO). Todo bom programador sabe que se deve tentar distribuir as responsabilidades (<em>concerns</em>) do programa em módulos, de forma que cada módulo seja fácil de implementar, entender e reusar. Em C, por exemplo, funções podem ser consideradas módulos. Pra qualquer programa não trivial, você não vai criar somente uma função <code>main()</code>, vai separar a funcionalidade em muitas funções que se chamam pra realizar o objetivo do software. Já OO prega a modularização do software em uma hierarquia de classes e conta com polimorfismo, herança, etc. A motivação de AOSD é que existem algum concerns que entrecortam a hierarquia, ou seja, que mesmo criando essa hierarquia de classes, você não tem como separar dois concerns que deveriam ser separados (para serem melhor implementados, entendidos e reusados).</p>
<p>Pra não ficar somente no abstrato, vamos à um exemplo bem simples, que é utilizado constantemente pra apresentar AOP. Imagine que você tem uma classe que faz o controle do acesso ao banco de dados. O código abaixo é um esboço de como uma classe dessas seria implementada em Java. Você tem um gerente de transações e, em todos os métodos de acesso ao banco de dados, você chama o gerente pra iniciar uma transação e fazer commit se tudo deu certo, ou rollback se deu algum problema. Note que hoje em dia ninguém faria um código assim, já que existem soluções melhores do que ficar escrevendo SQL no seu código (como <a href="http://www.hibernate.org" onclick="javascript:urchinTracker('/outbound/article/www.hibernate.org');">Hibernate</a>), mas é bem ilustrativo do problema.</p>
<pre>

public class DB {
	TransactionManager manager = ...;

	public void storeUser(User u) {
		manager.start();
		try {
			// write some sql code storing u into the DB
			manager.commit();
		} catch (DBException e) {
			manager.rollback();
		}
	}
	public void storeAccount(Account a) {
		manager.start();
		try {
			// write some sql code storing a into the DB
			manager.commit();
		} catch (DBException e) {
			manager.rollback();
		}
	}
	...
}</pre>
<p>Claramente dá pra perceber que eu tô misturando dois concerns na mesma classe. Um é persistência (salvar o User e a Account no banco de dados) e outro é controle de transações. Em OO, não tem um jeito elegante de separar esses concerns. Você pode até tentar fazer uma interface com uma callback pra tentar minimizar a repetição de código, como no código abaixo, mas não fica ideal.</p>
<pre>

public interface TransactionalTask {
	public void execute();
}
public class TransactionManager {
	TransactionManager manager = ...;

	public void executeInTransaction(TransactionalTask task) {
		manager.start();
		try {
			task.execute();
			manager.commit();
		} catch (DBException e) {
			manager.rollback();
		}
	}
	...
}
public class DB {
	public void storeUser(User u) {
		manager.executeInTransaction(new TransactionalTask() {
			public void execute() {
				// write some sql code storing u into the DB
			}
		});
	}
	...
}</pre>
<p>A idéia de AOSD é criar um novo módulo (chamado aspecto) em que você possa encapsular esses concerns que não tem como você modularizar com classes. AspectJ é a implementação mais conhecida de AOP, tanto por ser a primeira, quanto por ser bem robusta e contar com apoio de diversas empresas. Em AspectJ, que é uma extensão de Java (todo código Java é código AspectJ válido), nós criaríamos um aspecto pra encapsular controle de transações. O pseudo código abaixo mostra a idéia (eu não testei o código, então não garanto copy-and-paste funcionando).</p>
<pre>

public aspect TransactionManagerAspect {
	TransactionManager manager = ...;

	around(Object o) : execution(public void DB.*(..)) &amp;&amp; args(o) {
		manager.start();
		try {
			proceed(o);
			manager.commit();
		} catch (DBException e) {
			manager.rollback();
		}
	}
}

public class DB {

	public void storeUser(User u) {
		// write some sql code storing u into the DB
	}
	public void storeAccount(Account a) {
		// write some sql code storing a into the DB
	}
	...
}</pre>
<p>A classe DB agora contém somente código relativo à persistência e o aspecto é responsável pelo controle de transações. Em terminologia de AOSD, <code>around</code> é um tipo de <em>advice</em> e <code>execution</code> um tipo de <em>pointcut</em>. O que esse código tá dizendo é que sempre que a execução do programa for iniciar um método publico, que retorna void, na classe DB, o método deve ser substituído (por isso &#8220;around&#8221;) por esse advice aqui. O código do advice vai fazer o controle da transação e vai chamar <code>proceed</code> pra executar o código original. Note que o código do advice é muito parecido com a nossa solução usando callbacks. A grande novidade aqui é que usando pointcuts a gente consegue especificar quando que a &#8220;callback&#8221; deve ser usada, deixando o código da classe DB bem mais limpo.</p>
<p>Esse exemplo mostra a parte dinâmica da história, isto é, como usar aspectos pra &#8220;interceptar&#8221; alguns pontos da execução de um programa e inserir (ou remover) funcionalidade (código) nesses pontos. Mas AOSD também trata da parte estática ou &#8220;estrutural&#8221; da coisa. Por exemplo, imagine que no nosso exemplo nós quiséssemos inserir um controle de concorrência bem primitivo, pra garantir que ninguém modificou o <code>User</code> no tempo entre eu buscar no banco e salvar. Pra isso, eu poderia adicionar um campo na classe <code>User</code> com um contador que é incrementado sempre que ele for salvo no banco. Desta forma, na hora de salvar, eu confiro se o valor do contador no objeto que recebi é o mesmo do banco de dados. Se não for, significa que alguém alterou o objeto e eu recebi um objeto inconsistente. Novamente, o problema é que esse campo não faz parte do concern persistência ou modelo de dados. Portanto, não faria sentido eu declarar o contador na classe <code>User</code>. Pra resolver esse problema, AspectJ usa <em>intertype declarations</em>, que permitem a declaracão de campos e métodos em outras classes. Por exemplo, o código abaixo declara e inicializa um campo <code>counter</code> na classe <code>User</code>, removendo dela o concern tratamento de concorrência.</p>
<pre>

public aspect ConcurrencyManagerAspect {
	long User.counter = 0;
	...
}</pre>
<p><strong>Conceitos</strong></p>
<p>Quando eu estava descrevendo o exemplo eu me referi à alguns conceitos de AOSD. Mas acho importante deixar um pouco mais explícito, então seguem algumas definições.</p>
<p>Existem alguns eventos que acontecem durante a execução de um programa que são interessantes de serem interceptados. Esses pontos são chamados <em>join points</em>. Nós vimos que a execução de um método é um ponto interessante quando o objetivo é substituir o método ou introduzir funcionalidade antes ou depois do método. Outros join points, por exemplo, são a chamada de um método (não confundir com a execução), a leitura ou escrita de um campo, ou a inicialização estática de uma classe. Mas esses join points são eventos concretos que acontecem em tempo de execução. <em>Pointcuts</em> são um jeito de especificar de forma abstrata (por exemplo, com regular expressions) quais join points você quer interceptar. AspectJ oferece pointcuts primitivos pros join points mais importantes (como <code>execution</code>, <code>call</code>, <code>get</code>, etc) e outros pointcuts usados pra identificar os objetos envolvidos nos eventos e ligá-los a variáveis. No nosso exemplo, <code>args</code> foi usado pra pegar uma referência ao objeto passado como parâmetro ao método. Outros pointcuts importantes são <code>target</code> (e.g., o objeto que é o destino de uma chamada de método) e <code>this</code> (e.g., o objeto que faz a chamada).</p>
<p>Quando um join point acontece em runtime e ele faz match com um pointcut, então se executa o <em>advice</em> relativo ao pointcut (se tiver algum). Nós vimos como um advice do tipo <code>around</code> funciona. AspectJ também tem advices <code>before</code> e <code>after</code> (que pode ser <code>after throwing</code> ou <code>after returning</code>), que servem pra introduzir código antes ou depois do join point. <em>Intertype declarations</em> também são disponibilizadas por AspectJ pra introduzir novos campos métodos em outras classes, como vimos no exemplo.</p>
<p>Um aspecto é então um módulo usado pra encapsular todas essas construções, do mesmo jeito que uma classe encapsula métodos e campos. O objetivo principal de um aspecto é de modularizar um interesse (concern) que não faz parte da decomposição normal da hierarquia de classes. Esses concerns são chamados de <em>crosscutting concerns</em>, porque eles entrecortam a hierarquia. A implementação de um concern é dita espalhada (scattered) quando ela não está localizada, e entrelaçada (tangled) quando ela está misturada com outros concerns.</p>
<p>Pra quem tiver interesse, o <a href="http://www.eclipse.org/aspectj/doc/released/progguide/index.html" onclick="javascript:urchinTracker('/outbound/article/www.eclipse.org');">AspectJ Programming Guide</a> é um excelente tutorial com bons exemplos e referências pros diversos tipos de pointcuts, além de explicar alguns problemas que você pode encontrar quando não tiver muita experiência com aspectos.</p>
<p><strong>Discussão</strong></p>
<p>No texto acima eu tratei AOSD e AOP quase como sinônimos, mas eu quero enfatizar que são distintos. Orientação a aspectos surgiu como AOP, pois trazia soluções pra problemas diretamente ligados ao código, como no exemplo sobre controle de transações. Contudo, percebeu-se que seria interessante elevar o nível de abstração e que crosscutting concerns podiam também ser encontrados em design, arquitetura, análise de requisitos, etc. Então AOSD trata não só da programação, mas também de todo o conjunto de metodologias, processos, etc, ligados ao desenvolvimento de software usando a idéia de que crosscutting concerns devem ser tratados como &#8220;first class citizens&#8221;.</p>
<p>Na minha experiência, AOP como encontrada em AspectJ é utilizada quase que exclusivamente em círculos acadêmicos. Existem algumas empresas que adotam AspectJ para alguns projetos, mas a linguagem está longe de ser adotada em larga escala. Porém, alguns conceitos de AOP são muito usados em alguns frameworks e application servers como <a href="http://www.springframework.org" onclick="javascript:urchinTracker('/outbound/article/www.springframework.org');">Spring</a> e <a href="http://jboss.org" onclick="javascript:urchinTracker('/outbound/article/jboss.org');">JBoss</a>. Spring, por exemplo, tem o conceito de interceptors, que nada mais são do que pointcuts e advice, mas menos poderosos (não permitem interceptar join points de pouca granularidade, como getters, se não me engano).</p>
<p>Eu acredito que existem atualmente dois grandes impedimentos pra se usar AOP em larga escala. Primeiro é a tecnologia do compilador. Hoje em dia ninguém aceita trabalhar com um compilador que não seja incremental. Quando você usa Eclipse e faz uma alteração no código, o JDT só compila o necessário. O similar para AspectJ, AJDT, tenta fazer o mesmo. Porém, a tarefa é muito mais difícil, pois uma pequena mudança tem que ser verificada perante todos os pointcuts do seu sistema, pois de repente o que você mudou pode agora ser interceptado pelo pointcut. Assim, apesar de ter uma performance relativamente boa, trabalhar com AspectJ usando AJDT não é tao agradável quanto trabalhar com Java usando JDT.</p>
<p>Segundo, AOSD não vai acabar com todos os seus problemas. É difícil pros programadores entenderem os conceitos e leva tempo pra comunidade desenvolver design patterns e entender o que tirar de melhor do paradigma. Pointcuts são atualmente regular expressions, então eles são frágeis e qualquer mudança de nome de um método pode fazer um pointcut não mais interceptar aquele método, e você não tem como perceber que isso aconteceu. Suporte de boas ferramentas é então essencial. Além disso, eu tenho dúvidas de que aspectos sejam bons pra modularizar concerns heterogêneos como &#8220;logging&#8221;, que foi sempre um dos principais exemplos. O problema é que cada instância de logging é muito específica pro contexto, então não faz sentido você remover todas as chamadas de log e encapsular em um advice, pois o advice teria que ser diferente pra cada ponto que ele interceptasse. Controle de transações é homogêneo, pois o advice sempre faz a mesma coisa, então é um exemplo mais apropriado. Existem estudos que apontam que Mixin Layers são melhores pra concerns heterogêneos como logging, mas isso seria assunto para um outro post.</p>
<p>==========================<br />
Nota no dia 5/11</p>
<p>Conversando com o Miguel eu acabei percebendo algo que talvez não tenha ficado muito claro. AspectJ é uma extensão de Java e precisa de um compilador especial que compila as classes como se fossem Java e depois analisa os aspectos do sistema e faz diretamente as modificações no código (ou introduz testes de tempo de execução quando não tem como verificar estaticamente o resultado). Esse último passo, &#8220;introduzir os aspectos&#8221;, é chamado <em>weaving</em>.</p>
<p>Existem duas alternativas principais de compiladores pra AspectJ. O ajc é parte do <a href="http://www.eclipse.org/ajdt/" onclick="javascript:urchinTracker('/outbound/article/www.eclipse.org');">AJDT</a>, que é uma extensão do JDT do Eclipse. Como o JDT, o AJDT contém editor, compilador, debugger, e tudo o mais, implementados em plugins pro Eclipse. O principal objetivo do projeto é que a compilação seja rápida pra que você tenha a mesma experiencia que programando em Java, ou seja, ele tenta ser incremental e o código do compilador em si é otimizado (leia-se, não-facilmente extensível).</p>
<p>A outra alternativa é o abc (<a href="http://aspectbench.org" onclick="javascript:urchinTracker('/outbound/article/aspectbench.org');">Aspect Bench Compiler</a>), que é um compilador acadêmico cujo objetivo principal é ser extensível pra que se possa fazer pesquisa com linguagens de programação, otimização de código, análise estática, etc. Dessa forma, compilar um sistema grande com abc, principalmente usando as otimizações disponíveis, é bem demorado. O ideal é programar usando o AJDT e usar o abc pra gerar o bytecode de produção, já que ele é bem mais otimizado que o gerado pelo ajc.</p>
<p>Além disso, AspectJ não é a única linguagem orientada à aspectos derivada de Java. No site da aosd.net, por exemplo, tem uma lista com alguns <a href="http://aosd.net/wiki/index.php?title=Supported_Systems" onclick="javascript:urchinTracker('/outbound/article/aosd.net');">sistemas</a> (derivados ou não de Java) e algumas <a href="http://aosd.net/wiki/index.php?title=Tools_for_Developers" onclick="javascript:urchinTracker('/outbound/article/aosd.net');">ferramentas</a> orientadas a aspectos.</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=G0hEN"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=G0hEN" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=lsK1N"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=lsK1N" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/442663995" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/11/04/micro-introducao-sobre-orientacao-a-aspectos-aspectj/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/11/04/micro-introducao-sobre-orientacao-a-aspectos-aspectj/</feedburner:origLink></item>
		<item><title>Links for 2008-10-31 [del.icio.us]</title><link>http://feeds.feedburner.com/~r/log4dev/xml/~3/438749062/log4dev</link><pubDate>Sat, 01 Nov 2008 00:00:00 -0500</pubDate><guid isPermaLink="false">http://del.icio.us/log4dev#2008-10-31</guid><content:encoded><![CDATA[<ul>
<li><a href="http://www.25hoursaday.com/weblog/2008/10/31/PlatformMonetizationIsATwoWayStreetLessonsFromFacebookAndSunMicrosystems.aspx">Dare Obasanjo aka Carnage4Life - Platform Monetization is a Two Way Street: Lessons from Facebook and Sun Microsystems</a></li>
</ul><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/438749062" height="1" width="1"/>]]></content:encoded><description>&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.25hoursaday.com/weblog/2008/10/31/PlatformMonetizationIsATwoWayStreetLessonsFromFacebookAndSunMicrosystems.aspx"&gt;Dare Obasanjo aka Carnage4Life - Platform Monetization is a Two Way Street: Lessons from Facebook and Sun Microsystems&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;</description><feedburner:origLink>http://del.icio.us/log4dev#2008-10-31</feedburner:origLink></item><item><title>Links for 2008-10-29 [del.icio.us]</title><link>http://feeds.feedburner.com/~r/log4dev/xml/~3/436561041/log4dev</link><pubDate>Thu, 30 Oct 2008 00:00:00 -0500</pubDate><guid isPermaLink="false">http://del.icio.us/log4dev#2008-10-29</guid><content:encoded><![CDATA[<ul>
<li><a href="http://www.scriptol.org/list-of-algorithms.html">List of all algorithms, classified by purpose</a><br/>
A complete list of all major algorithms (300), in any domain</li>
</ul><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/436561041" height="1" width="1"/>]]></content:encoded><description>&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.scriptol.org/list-of-algorithms.html"&gt;List of all algorithms, classified by purpose&lt;/a&gt;&lt;br/&gt;
A complete list of all major algorithms (300), in any domain&lt;/li&gt;
&lt;/ul&gt;</description><feedburner:origLink>http://del.icio.us/log4dev#2008-10-29</feedburner:origLink></item><item><title>Links for 2008-10-28 [del.icio.us]</title><link>http://feeds.feedburner.com/~r/log4dev/xml/~3/435466742/log4dev</link><pubDate>Wed, 29 Oct 2008 00:00:00 -0500</pubDate><guid isPermaLink="false">http://del.icio.us/log4dev#2008-10-28</guid><content:encoded><![CDATA[<ul>
<li><a href="http://www.sliderocket.com/">SlideRocket - The Best Online Presentation Software.</a></li>
</ul><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/435466742" height="1" width="1"/>]]></content:encoded><description>&lt;ul&gt;
&lt;li&gt;&lt;a href="http://www.sliderocket.com/"&gt;SlideRocket - The Best Online Presentation Software.&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;</description><feedburner:origLink>http://del.icio.us/log4dev#2008-10-28</feedburner:origLink></item><item>
		<title>SlideRocket</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/434640698/</link>
		<comments>http://log4dev.com/2008/10/28/sliderocket/#comments</comments>
		<pubDate>Tue, 28 Oct 2008 11:53:45 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Ferramentas]]></category>

		<category><![CDATA[Produto]]></category>

		<category><![CDATA[Adobe]]></category>

		<category><![CDATA[Flex]]></category>

		<category><![CDATA[Slideshow]]></category>

		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/10/28/sliderocket/</guid>
		<description><![CDATA[Uma ótima alternativa para aqueles que precisam criar apresentações, não são chegados em PowerPoint, querem ter a possibilidade de usar a web como plataforma e querem fugir dos tentáculos do Google: SlideRocket (www.sliderocket.com). 
Baseado na tecnologia Adobe Flex e Adobe AIR, o SlideRocket permite criar, compartilhar e exibir apresentações online. Os pontos fortes do sistema [...]]]></description>
			<content:encoded><![CDATA[<p>Uma ótima alternativa para aqueles que precisam criar apresentações, não são chegados em PowerPoint, querem ter a possibilidade de usar a web como plataforma e querem fugir dos tentáculos do Google: <a href="http://www.sliderocket.com" onclick="javascript:urchinTracker('/outbound/article/www.sliderocket.com');">SlideRocket (www.sliderocket.com). </a></p>
<p>Baseado na tecnologia <a href="http://www.adobe.com/products/flex/" onclick="javascript:urchinTracker('/outbound/article/www.adobe.com');">Adobe Flex</a> e <a href="http://www.adobe.com/products/air/" onclick="javascript:urchinTracker('/outbound/article/www.adobe.com');">Adobe AIR</a>, o <strong>SlideRocket</strong> permite criar, compartilhar e exibir apresentações online. Os pontos fortes do sistema são a interface de criação de slides, a qualidade do resultado e a possibilidade de exibir online (em modo fullscreen) ou de criar um executável para o Desktop com o AIR.</p>
<p>Tive a oportunidade de ver uma apresentação utilizando esta ferramenta, e achei os resultados surpreendentes. Segundo um amigo marketeiro e criador constante de apresentações, apesar de alguns bugs a facilidade de uso vale a pena. Em alguns casos, como incluir vídeos em Flash, o software  é inclusive superior ao Powerpoint. <span dir="ltr" id=":15i"></span></p>
<p>O sistema oferece 3 opções de  planos. O plano gratuíto oferece 250MB de espaço, ferramentas de criação e número ilimitado de apresentações (desde que não ultrapassem os 250MB, obviamente&#8230;). Os planos pagos oferecem, entre outras coisas, mais espaço e possibilidade de controle de versão.</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=k2QJM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=k2QJM" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=BLDhM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=BLDhM" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/434640698" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/10/28/sliderocket/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/10/28/sliderocket/</feedburner:origLink></item>
		<item>
		<title>Vazamento de memória em Java</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/431999335/</link>
		<comments>http://log4dev.com/2008/10/25/vazamento-de-memoria-em-java/#comments</comments>
		<pubDate>Sat, 25 Oct 2008 20:14:42 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Desenvolvimento]]></category>

		<category><![CDATA[Java]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/10/25/vazamento-de-memoria-em-java/</guid>
		<description><![CDATA[Isso existe?!
Sim&#8230;.
Uma das grandes coisas que Java trouxe para o mundo do desenvolvimento foi uma moderna JVM, e um Garbage Colector eficiente, que foi se aprimorando ao longo dos anos. Com isto, o desenvolvedor pode deixar de se preocupar com questões de alocação e liberação de memória, fontes de perdas de cabelos e noites de [...]]]></description>
			<content:encoded><![CDATA[<p><strong>Isso existe?!</strong></p>
<p>Sim&#8230;.</p>
<p>Uma das grandes coisas que Java trouxe para o mundo do desenvolvimento foi uma moderna JVM, e um Garbage Colector eficiente, que foi se aprimorando ao longo dos anos. Com isto, o desenvolvedor pode deixar de se preocupar com questões de alocação e liberação de memória, fontes de perdas de cabelos e noites de sono perdidas de muitos programadores C/C++.</p>
<p>Nestas linguagens, um vazamento de memória se caracteriza como sendo uma região do heap alocada pelo desenvolvedor em algum momento do ciclo de vida de um software, cujo ponteiro se perde. Assim sendo, fica impossível (ou pelo menos extremamente difícil) recuperar esta área de memória para uso futuro. O efeito imediato é que o consumo de memória vai aumentando com o tempo, até tornar o sistema inviável.</p>
<p>É fato que este tipo de situação não existe em Java, uma vez que em última instância, a JVM sempre terá uma referência para uma área de memória alocada pelo desenvolvedor, e cuidará de fazer a limpeza caso necessário. Mágica? Não, tecnologia. Explicando de forma beeeeeeeeeeem resumida, o GC mantém uma contagem de quantas referências criadas pelo desenvolvedor apontam para um determinado objeto. Quando este contador chega a zero, está na hora de limpar a memória, pois com certeza esta não será mais útil.</p>
<p>Fica claro então que áreas de memória nunca serão perdidas em Java.</p>
<p><strong>Miguel, você bebeu? Como é que vazamentos podem ocorrer então? </strong></p>
<p>Bom, quem nunca perde a referência é a JVM.  Mas é possível perder o controle das referências para um objeto. Como eu disse antes, o GC coleta objetos sem referência. Mas e se você esquecer que tem referências perdidas no código e não zerá-las? Aí o objeto nunca será removido, e podemos ter um vazamento de memória, segundo Java. Para apaziguar certos ânimos, passarei a chamar este problema de <strong>Travamento de memória</strong>.</p>
<p>A boa notícia é que é bem mais fácil consertar em Java, e isto só se torna um problema real em grandes projetos que criam muitos objetos ao longo do tempo. Se você desenvolve exclusivamente para Web usando servidores de aplicação como JBoss, provavelmente pode fechar este artigo e voltar às suas atividades cotidianas.</p>
<p>A má notícia é que como se criou o mito de que este tipo de situação é impossível, ninguém hoje em dia se preocupa mais com isso. Não que isto seja ruim por si só. O problema é que quando suspeitamos de que isso pode estar acontecendo, consertar pode ficar mais complexo.</p>
<p>Uma situação clássica que pode gerar travamentos é o uso de Observers/Observables. Suponha que você tenha um objeto A do tipo Observable, e que ao longo da vida do seu software, você crie constantemente novas intâncias de objetos do tipo B que se cadastram com observadores de A. Nesta arquitetura, A contém referências a todos as intâncias de B, de forma não explícita (ou seja, contém referências à interface Observer). Basta alguém esquecer de limpar a referência da lista de observers e pronto&#8230;memória travada!</p>
<p>Como resolver isso? Bem, tentar racionalizar o processo de criação e limpeza de objetos, centralizando estes processos em pontos bem controlados. O processo de &#8220;limpeza&#8221; de recursos é muito importante, sobretudo quando a árvore de objetos e referências for grande.</p>
<p>==========================</p>
<p>Nota do dia 26/10</p>
<p>Como bem lembrado pelo leitor Thiago, uma outra possível solução é o uso de WeakReferences em Java. Um objeto deste tipo funciona como uma referência normal em Java, mas não trava o GC: caso um objeto seja referenciado apenas por WeakReferences, ele será coletado normalmente. Vale a pena olhar este artigo:</p>
<p><a href="http://www.ibm.com/developerworks/java/library/j-jtp11225/index.html" onclick="javascript:urchinTracker('/outbound/article/www.ibm.com');">http://www.ibm.com/developerworks/java/library/j-jtp11225/index.html </a></p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=AZInM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=AZInM" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=fHdJM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=fHdJM" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/431999335" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/10/25/vazamento-de-memoria-em-java/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/10/25/vazamento-de-memoria-em-java/</feedburner:origLink></item>
		<item>
		<title>No Twitter, again</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/430648356/</link>
		<comments>http://log4dev.com/2008/10/24/no-twitter-again/#comments</comments>
		<pubDate>Fri, 24 Oct 2008 12:01:24 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Twitter]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/10/24/no-twitter-again/</guid>
		<description><![CDATA[Post rápido, apenas para anunciar que o usuário @log4dev no Twitter foi reativado. Na prática isto significa que novos textos serão divulgados na plataforma, e eventualmente links e curiosidades.
]]></description>
			<content:encoded><![CDATA[<p>Post rápido, apenas para anunciar que o usuário <a href="http://twitter.com/log4dev" onclick="javascript:urchinTracker('/outbound/article/twitter.com');">@log4dev</a> no Twitter foi reativado. Na prática isto significa que novos textos serão divulgados na plataforma, e eventualmente links e curiosidades.</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=l7hXM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=l7hXM" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=zF4YM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=zF4YM" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/430648356" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/10/24/no-twitter-again/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/10/24/no-twitter-again/</feedburner:origLink></item>
		<item>
		<title>Java, Emacs and JaL (Java, a Linguagem)</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/421521316/</link>
		<comments>http://log4dev.com/2008/10/15/java-emacs-and-jal-java-a-linguagem/#comments</comments>
		<pubDate>Wed, 15 Oct 2008 12:20:18 +0000</pubDate>
		<dc:creator>Alexandre</dc:creator>
		
		<category><![CDATA[Uncategorized]]></category>

		<category><![CDATA[Java Emacs]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/10/15/java-emacs-and-jal-java-a-linguagem/</guid>
		<description><![CDATA[
Comecei a utilizar Emacs no início da minha primeira iniciação científica, nos idos de 1999. Fui feliz durante muito tempo, escrevendo código em Perl e C, algumas páginas HTML, diversos relatórios em Latex &#8230; tudo muito tranqüilo, nenhuma reclamação com aquele ambiente de desenvolvimento. 
Eis que por volta de 2002, ao definir a linguagem de [...]]]></description>
			<content:encoded><![CDATA[<p><img src="http://imgs.xkcd.com/comics/real_programmers.png" align="texttop" height="329" width="600" alt="Real programmers" style="border-width: 1px; border-color: black; border-style: solid" /></p>
<p>Comecei a utilizar <strong>Emacs</strong> no início da minha primeira iniciação científica, nos idos de 1999. Fui feliz durante muito tempo, escrevendo código em Perl e C, algumas páginas HTML, diversos relatórios em Latex &#8230; tudo muito tranqüilo, nenhuma reclamação com aquele ambiente de desenvolvimento. </p>
<p>Eis que por volta de 2002, ao definir a linguagem de programação que iríamos utilizar na <a href="http://www.scylla.com.br" onclick="javascript:urchinTracker('/outbound/article/www.scylla.com.br');">Scylla</a>, optamos por <strong>Java</strong>, uma linguagem até então desconhecida para mim. Arregacei as mangas, peguei meu <strong>Emacs</strong>, e mandei bala. Tudo muito tranqüilo, afinal não tinha parâmetro de comparação. Até que fui apresentado ao <strong>Eclipse</strong>: <em>auto-complete</em>, <em>code-checking</em> durante a digitação, etc e tal - Como pude viver sem isso? - programar em Java ficou muito fácil.</p>
<p>Tudo ia muito bem, até há pouco tempo atrás, quando por razões que nem o Padre Quevedo poderia explicar, a configuração de meu ambiente de desenvolvimento foi para o espaço, sem formas de recuperá-lo. Isto, associado à vontade dos orixás da conexão internet intermitente (vulgo péssima estrutura de TI), impediram que eu conseguisse baixar uma outra versão do meu querido <strong>Eclipse</strong>. Após falhar neste teste de paciência, decidi que tinha de voltar a trabalhar com o que eu tinha à mão. Resultado: tirei a poeira do <strong>Emacs</strong> e o coloquei para trabalhar.</p>
<p>O começo foi duro: vários impropérios foram proferidos por conta de erros de digitação que resultavam em erros de compilação; sem contar no aumento de caracteres que tive que passar a digitar - já não me lembrava mais que era preciso escrever imports (aliás, não lembrava que a classe <em>Connection</em> estava em <em>java.sql</em> e que a classe <em>DataSource</em> em <em>javax.sql</em> ?). Mas muitos xingos e litros de café depois, me adaptei a esta nova realidade.Neste instante, compreendi claramente a diferença entre <a href="http://log4dev.com/2007/09/27/viva-a-diversidade/" >JaL e JaP - (Java a Linguagem x Java a Plataforma - veja os comentários)</a>. </p>
<p>Não quero defender aqui que a verbosidade de Java, condenada veementemente por alguns, seja um impedimento ao uso da linguagem ( devagar com as críticas Lullis, por favor <img src='http://log4dev.com/wp-includes/images/smilies/icon_biggrin.gif' alt=':-D' class='wp-smiley' /> ), mas vejo esta verbosidade como um atributo para melhorar sua forma de programar. Agora, penso melhor no código que escrevo, procuro formas de reaproveitar o código &#8230; até mesmo os nomes das variáveis que utilizo são pensadas de forma a <em>evitar a fadiga</em>. Coisas que eu não tinha porque me preocupar, pois tudo era muito simples, graças ao poder do <em>Ctrl Enter</em>.</p>
<p>Não defendo tampouco a aposentadoria de ferramentas como o <strong>Eclipse</strong>. Gostaria de voltar a utilizá-lo no futuro. Mas neste instante, pretendo continuar a utilizar o <strong>Emacs</strong> por um bom tempo, forçando-me a melhorar minhas práticas, e então sim, voltar para o <strong>Eclipse</strong>, que inegavelmente é uma ferramenta fantástica para aumento de produtividade.</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=ViAFM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=ViAFM" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=2JRgM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=2JRgM" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/421521316" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/10/15/java-emacs-and-jal-java-a-linguagem/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/10/15/java-emacs-and-jal-java-a-linguagem/</feedburner:origLink></item>
		<item>
		<title>Rapidinha</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/419512558/</link>
		<comments>http://log4dev.com/2008/10/13/rapidinha/#comments</comments>
		<pubDate>Mon, 13 Oct 2008 13:19:51 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Desenvolvimento]]></category>

		<category><![CDATA[Ajax]]></category>

		<category><![CDATA[Django]]></category>

		<category><![CDATA[Javascript]]></category>

		<category><![CDATA[Python]]></category>

		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/10/13/rapidinha/</guid>
		<description><![CDATA[Só pra falar algo que talvez já seja óbvio pro pessoal mais esperto: o trio Python/Django/Prototype (Scriptaculous) tem um poder incrível de ajudar a desenvolver coisas úteis, eficientes e bonitas em pouquíssimo tempo. A minha produtividade com esta trinca tem sido muito grande, fator essencial para a evolução dos meus projetos pessoais (job4dev e sigaseutime).
]]></description>
			<content:encoded><![CDATA[<p>Só pra falar algo que talvez já seja óbvio pro pessoal mais esperto: o trio Python/Django/Prototype (Scriptaculous) tem um poder incrível de ajudar a desenvolver coisas úteis, eficientes e bonitas em pouquíssimo tempo. A minha produtividade com esta trinca tem sido muito grande, fator essencial para a evolução dos meus projetos pessoais (<a href="http://job4dev.com" onclick="javascript:urchinTracker('/outbound/article/job4dev.com');">job4dev</a> e <a href="http://www.sigaseutime.com.br" onclick="javascript:urchinTracker('/outbound/article/www.sigaseutime.com.br');">sigaseutime</a>).</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=OZlmM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=OZlmM" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=zyuzM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=zyuzM" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/419512558" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/10/13/rapidinha/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/10/13/rapidinha/</feedburner:origLink></item>
		<item>
		<title>Speedy “não pode mais dar acesso à Internet”!</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/412764221/</link>
		<comments>http://log4dev.com/2008/10/06/speedy-nao-pode-mais-dar-acesso-a-internet/#comments</comments>
		<pubDate>Mon, 06 Oct 2008 12:48:34 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Opinião]]></category>

		<category><![CDATA[Internet]]></category>

		<category><![CDATA[Mercado]]></category>

		<category><![CDATA[Speedy]]></category>

		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/10/06/speedy-nao-pode-mais-dar-acesso-a-internet/</guid>
		<description><![CDATA[Nota publicada no site do Speedy (http://www.speedy.com.br/comunicado.asp)
Atendendo a decisão judicial a Telefônica não pode mais prestar o &#8220;acesso&#8221; à internet diretamente aos clientes do Speedy.
A partir de 21 de agosto de 2008, para utilizar o Speedy os novos clientes deverão contratar um dos diversos provedores de acesso à internet existentes no mercado. Alguns destes provedores, [...]]]></description>
			<content:encoded><![CDATA[<p>Nota publicada no site do <a href="http://www.speedy.com.br/comunicado.asp" onclick="javascript:urchinTracker('/outbound/article/www.speedy.com.br');">Speedy (http://www.speedy.com.br/comunicado.asp)</a></p>
<blockquote><p>Atendendo a decisão judicial a Telefônica não pode mais prestar o &#8220;acesso&#8221; à internet diretamente aos clientes do Speedy.</p>
<p>A partir de 21 de agosto de 2008, para utilizar o Speedy os novos clientes deverão contratar um dos diversos provedores de acesso à internet existentes no mercado. Alguns destes provedores, em parceria com a Telefônica, fazem ofertas especiais para clientes Speedy.</p>
<p>Os clientes Speedy que realizam o acesso à Internet diretamente pela Telefônica, receberão um comunicado específico estabelecendo a data limite para contratação de um dos provedores disponíveis no mercado.</p></blockquote>
<p>OK, na prática isto quer dizer que aquele usuário internet@speedy.com.br não irá mais funcionar.</p>
<p>Mas o mais interessante é notar na cara de pau da primeira frase:  &#8220;Atendendo a decisão judicial a Telefônica <strong>não pode </strong>mais <strong>prestar o &#8220;acesso&#8221; à internet</strong> diretamente aos clientes do Speedy.&#8221;. Primeiro por que deixa a entender que a empresa estava permitindo acesso direto sem necessidade de provedor externo de autenticação por vontade própria, o que é falso: foi uma liminar da justiça de São Paulo que a obrigou a fazer isso.</p>
<p>Segundo porque o texto faz parecer que o tal acesso é algum serviço complexo prestado por ela. Ora, todos sabemos que o tal &#8220;acesso&#8221; se resume a simplesmente verificar uma senha em uma base de dados! E além do mais, o único serviço prestado de fato pela Telefônica é o de fornecer o acesso à Internet!</p>
<p>Aos descontentes, eu diria que existem basicamente dois caminhos: um caminho possível é mudar de provedor de banda larga, para um que realmente possa oferecer acesso à Internet. A outra é entrar na Justiça. Um bom ponto de início para isso seria o site <a href="http://www.abusar.org.br/" onclick="javascript:urchinTracker('/outbound/article/www.abusar.org.br');">ABUSAR (http://www.abusar.org.br/)</a>.</p>
<p>===========================================</p>
<p><strong>NOTA DO DIA 07/11/2008</strong></p>
<p><strong>A partir de hoje, o Speedy realmente não pode mais dar acesso sem um provedor externo. Veja mais em <a href="http://log4dev.com/2008/11/07/speedy-agora-realmente-nao-pode-mais/ " >http://log4dev.com/2008/11/07/speedy-agora-realmente-nao-pode-mais/ </a></strong></p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=olf4M"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=olf4M" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=5lAXM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=5lAXM" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/412764221" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/10/06/speedy-nao-pode-mais-dar-acesso-a-internet/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/10/06/speedy-nao-pode-mais-dar-acesso-a-internet/</feedburner:origLink></item>
		<item>
		<title>Máquina do tempo</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/408191512/</link>
		<comments>http://log4dev.com/2008/10/01/maquina-do-tempo/#comments</comments>
		<pubDate>Wed, 01 Oct 2008 12:08:34 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Idéias]]></category>

		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Pesquisa]]></category>

		<category><![CDATA[Google]]></category>

		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/10/01/maquina-do-tempo/</guid>
		<description><![CDATA[O Google está comemorando 10 anos, e para a ocasião, sairam atrás de relíquias guardadas no fundo de algum servidor perdido no Googleplex. Encontraram um arquivo de indices de busca de 2001, que depois de alguns ajustes, foi restaurado. Obviamente eles não poderiam deixar de colocar isso no ar, e como nada no Google é [...]]]></description>
			<content:encoded><![CDATA[<p>O <strong>Google</strong> está comemorando 10 anos, e para a ocasião, sairam atrás de relíquias guardadas no fundo de algum servidor perdido no Googleplex. Encontraram um <strong>arquivo de indices de busca de 2001</strong>, que depois de alguns ajustes, foi restaurado. Obviamente eles não poderiam deixar de colocar isso no ar, e como nada no Google é deixado ao acaso, eles ainda restauraram as páginas da época, à partir do cache deles.</p>
<p>Esta brincadeirinha, disponível para acesso <a href="http://www.google.com/search2001.html" onclick="javascript:urchinTracker('/outbound/article/www.google.com');">aqui</a> (http://www.google.com/search2001.html) permite fazer duas coisas interessantes. A primeira é relembrar como era a Internet de 2001, quais os assuntos na moda e quais os termos que ainda estavam por vir. A segunda é ver como o design das páginas evoluiu nestes 7 anos, pois é possível ver a versão atual da página e a versão da época.</p>
<p>Fiz a busca pela palavra iTunes, e comparei os dois primeiros resultados. O primeiro é o site da Apple, <a href="http://web.archive.org/web/20011217002903/www.apple.com/itunes/" onclick="javascript:urchinTracker('/outbound/article/web.archive.org');">versão 2001</a> e <a href="http://www.apple.com/itunes/" onclick="javascript:urchinTracker('/outbound/article/www.apple.com');">versão 2008 </a>. O outro é um artigo da revista Business Week, sobre o tocador, O texto original continua lá, mas o design da página mudou bastante, de <a href="http://web.archive.org/web/20011211221558/www.businessweek.com/bwdaily/dnflash/jan2001/nf20010124_897.htm" onclick="javascript:urchinTracker('/outbound/article/web.archive.org');">2001</a> para <a href="http://www.businessweek.com/bwdaily/dnflash/jan2001/nf20010124_897.htm" onclick="javascript:urchinTracker('/outbound/article/www.businessweek.com');">hoje</a>.</p>
<p>Mais informações podem ser encontradas no <a href="http://googleblog.blogspot.com/2008/09/2001-search-odyssey.html" onclick="javascript:urchinTracker('/outbound/article/googleblog.blogspot.com');">Official Google Blog</a>.</p>
<p>======================================================</p>
<p><strong>Correção: como foi bem anotado pelo nosso leitor esquentadinho Luis, digno habitante do mundo real (porque o meu aparentemente é o mundo de Alice, quiçá da Lua) , o cache das páginas vem do <a href="http://www.archive.org/web/web.php" onclick="javascript:urchinTracker('/outbound/article/www.archive.org');">Internet Archive</a> que, confesso, eu não conhecia. Mas é culpa da mídia do meu mundo, um tanto quanto lerda&#8230;. </strong></p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=Zs5hM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=Zs5hM" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=HaBNM"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=HaBNM" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/408191512" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/10/01/maquina-do-tempo/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/10/01/maquina-do-tempo/</feedburner:origLink></item>
		<item>
		<title>Citação do dia</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/406294338/</link>
		<comments>http://log4dev.com/2008/09/29/citacao-do-dia/#comments</comments>
		<pubDate>Mon, 29 Sep 2008 14:11:59 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Desenvolvimento]]></category>

		<category><![CDATA[Opinião]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/09/29/citacao-do-dia/</guid>
		<description><![CDATA[Lida no Manifesto 37 Signals, versão original (que eu nunca tinha lido)
 My Cousin&#8217;s Buddy is a Web Designer
Then let him do it.
The money you save by using your cousin&#8217;s buddy is nothing compared with the cost in time and money required to undo his mistakes.
Simples. Perfeito.
]]></description>
			<content:encoded><![CDATA[<p>Lida no <a href="http://37signals.com/24.html" onclick="javascript:urchinTracker('/outbound/article/37signals.com');">Manifesto 37 Signals</a>, versão original (que eu nunca tinha lido)</p>
<blockquote><p> My Cousin&#8217;s Buddy is a Web Designer</p>
<p>Then let him do it.</p>
<p>The money you save by using your cousin&#8217;s buddy is nothing compared with the cost in time and money required to undo his mistakes.</p></blockquote>
<p>Simples. Perfeito.</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=R0LEL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=R0LEL" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=E1YxL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=E1YxL" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/406294338" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/09/29/citacao-do-dia/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/09/29/citacao-do-dia/</feedburner:origLink></item>
		<item>
		<title>Motivos para se ter um Mac</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/404726998/</link>
		<comments>http://log4dev.com/2008/09/27/motivos-para-se-ter-um-mac/#comments</comments>
		<pubDate>Sat, 27 Sep 2008 15:16:11 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Ferramentas]]></category>

		<category><![CDATA[Opinião]]></category>

		<category><![CDATA[Produto]]></category>

		<category><![CDATA[Apple]]></category>

		<category><![CDATA[Mac OS]]></category>

		<category><![CDATA[Windows]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/09/27/motivos-para-se-ter-um-mac/</guid>
		<description><![CDATA[ A história da familia Galves (também conhecida como minha familia) com o Mac tem exatamente 20 anos. Começou em 1988, quando meus pais compraram um Mac SE com incríveis 20MHz de processamento e 1MB de memória RAM. O motivo na época era a incrível superioridade de sua interface gráfica em relação aos PCs equipados com [...]]]></description>
			<content:encoded><![CDATA[<p> A história da familia Galves (também conhecida como minha familia) com o Mac tem exatamente 20 anos. Começou em 1988, quando meus pais compraram um <a href="http://en.wikipedia.org/wiki/Macintosh_SE" onclick="javascript:urchinTracker('/outbound/article/en.wikipedia.org');">Mac SE</a> com incríveis 20MHz de processamento e 1MB de memória RAM. O motivo na época era a incrível superioridade de sua interface gráfica em relação aos PCs equipados com DOS.</p>
<p>De lá para cá, foram um Performa, três iMacs, um eMac e alguns notebooks. E em todas as aquisições, sempre tinha o lado de &#8220;Apple é coisa de rico, é elitista, não tem assistência técnica no Brasil&#8230;&#8221;. Não deixava de ser verdade. Mas tem algo no ar: a percepção e a visão do público em relação à Apple está, em minha humilde opinião, mudando. Eu vejo a quantidade de pessoas a minha volta, computeiros ou não, que hoje pensam seriamente em comprar um MacBook, ou um MacBookPro, ou um iMac. Com certeza, a adoção da plataforma Intel, o dólar favorável e consequentemente a redução dos preços ajudou bastante. O efeito iPod/iPhone também. E em geral todos eles ficam extremamente felizes com a troca.</p>
<p>Motivos para se ter um Mac acho que não faltam. Vou listar alguns aqui, que para mim são bem importantes, e que acho que podem ser importantes para o público deste blog.</p>
<p>Antes do Mac O X, o grande trunfo do sistema operacional da Apple, além de sua usabilidade excepcional, era a sua altíssima integração com o hardware. Isso lhe dava a estabilidade que muitas vezes faltava ao Windows, que tinha (e ainda tem que) dar suporte à uma infinidade de drivers e periféricos, muitas vezes de baixa qualidade. Por este motivo muitos aplicativos complexos (como Photoshop) apresentavam benchmarks melhores no Mac do que em PCs com processadores mais rápidos.</p>
<p>Mas com o OS X, baseado no BSD e no microkernel Mach, a Apple adotou de vez as qualidades dos sistemas UNIX Like: um sistema realmente multiusuário, multitarefa preemptivo, com memória compartilhada. Ou seja, além do hardware extremamente bem controlado, agora o <strong>Mac oferece um SO moderno, eficiente e muito mais robusto</strong>.</p>
<p>E daí os leitores me perguntam: &#8220;se OS X é Unix like, porquê então gastar os tudos num Mac se eu posso ter um PC mais barato rodando Linux?&#8221; Boa pergunta! Eu diria que a resposta está nos detalhes. Eu gosto muito de Linux, tanto que recentemente mandei o Windows da minha máquina de trabalho pro espaço e instalei o Ubuntu. E isso com certeza aumentou muito a minha produtividade e felicidade. Inclusive, fiquei extremamente bem impressionado com a evolução do processo de instalação e da interface gráfica do Linux, dos quais eu estava afastado desde 2006.</p>
<p>Mas eu ainda tenho um pé atrás com ter Linux no meu computador pessoal. Porquê tem horas que eu quero desenvolver, hackear o sistema, fazer scripts. Mas em muitos momentos eu quero simplesmente que as coisas funcionem, quero que minhas placas de rede, vídeo, câmera embutida, HDs externos e afins sejam reconhecidos e integrados ao resto do sistema sem ter que ficar pesquisando horas em fóruns. As vezes quero não ter que escolher entre as milhares de opções de aplicativos para música ou vídeo. E sobretudo: eu sempre quero ter uma interface gráfica que funcione perfeitamente, que seja redonda e bonita. <strong>E aí chegamos ao outro grande trunfo da Apple: colocar uma interface gráfica matadora por cima do Unix, chamada Aqua</strong>. A Sun parece ter desistido de tentar fazer isso há um bom tempo, porquê o ambiente gráfico de suas estações de trabalho são muito fracos. O KDE e o Gnome me parecem estar no caminho certo, e estão bem pertos de ter um ambiente pronto para usuário final.</p>
<p>Até agora eu só falei do software. <strong>E o hardware, não tem nenhuma vantagem?</strong> Bom, se olharmos friamente apenas características como placa mãe, placas de vídeo, rede, processador, talvez não. <strong>Mas de novo, a diferença está nos detalhes</strong>. Está no conector magnético do cabo de energia (que já me salvou de desastres umas três vezes). Está na câmera embutida de altíssima qualidade. Está no teclado do MacBookPro com backlight, que ajuda muito a escrever em situações de baixa luminosidade. Está no acelerômetro que proteje o HD em movimentos bruscos. E sobretudo: está no design incrível, que permite que máquinas sejam clean, leves e finas. Além de bonitas. Acho isso bem importante.</p>
<p>&#8220;OK, OK, e os aplicativos do mundo Windows que eu amo tanto? Existe equivalência? E eu posso integrar um Mac no ambiente Windows da minha casa ou trabalho?&#8221;.</p>
<p>Sim, na grande maioria dos casos. Pacote Office da M$ (que é sagrado para boa parte da população usuária de Windows) existe para Mac, e tem compatibilidade total com o pacote para Windows. Aplicativo de IM, como MSN, Skype tem verão nativa, e existem vários programas que são compatíveis com GTalk, ICQ e MSN. Grande parte das ferramentas de processamento de imagens como Photoshop, Lightroom e outras tem versões nativas. O OS X é compatível com redes Windows, permitindo que arquivos sejam compartilhados entre Macs e PCs de forma transparente. Boa parte das impressoras oferece drives para ambos os sistemas operacionais e o processo de instalação é bem simples.</p>
<p><strong>E se tudo mais falhar, ainda existe a opção de instalar Windows dentro de uma máquina virtual, com o Virtual Box da Sun, ou o VMWare Fusion ou o Paralels</strong>. Instalei o VMWare Fusion no meu MacBookPro, e o resultado é muito bom. A versão 2.0, divulgada há pouco tempo permite que aplicativos Windows rodem de forma completamente integrada no ambiente Mac, sem a necessidade de uma janela da máquina virtual, e permite que atalhos sejam criados no sistema para ativação automática. Além do mais, eles garantem a compatibilidade total de vários jogos.</p>
<p>&#8220;Ahá, peguei você: JOGOS! A listinha de vinte e poucos jogos que rodam no VMWare Fusion não me impressiona. E aí?&#8221;. Pois é, chegamos ao único ponto sensível: jogos. A lista de jogos que estão sendo publicados para Mac está aumentando, mas ainda não chega aos pés da lista de jogos pra Windows. Mas neste caso, <strong>existe sempre a possibilidade de se instalar o Windows diretamente no Mac com um sistema de dual boot</strong>. Neste caso, todos os jogos rodam perfeitamente.</p>
<p>E para todo o resto, existe o Mac OS.</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=qdQ9L"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=qdQ9L" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=bt7rL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=bt7rL" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/404726998" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/09/27/motivos-para-se-ter-um-mac/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/09/27/motivos-para-se-ter-um-mac/</feedburner:origLink></item>
		<item>
		<title>iPhone: preços definidos.</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/403236008/</link>
		<comments>http://log4dev.com/2008/09/25/iphone-precos-definidos/#comments</comments>
		<pubDate>Thu, 25 Sep 2008 23:12:11 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Negocios]]></category>

		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Apple]]></category>

		<category><![CDATA[iPhone]]></category>

		<category><![CDATA[Mercado]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/09/25/iphone-precos-definidos/</guid>
		<description><![CDATA[A Folha confirmou: Vivo e Claro lançam no dia 26 (vulgo amanhã).
Preços: de 1000 a 3000 na Claro, e de 899 a 2199 na Vivo.
Acho que não será agora que terei meu iPhone. Muito caro!
]]></description>
			<content:encoded><![CDATA[<p>A Folha confirmou: Vivo e Claro lançam no dia 26 (vulgo amanhã).</p>
<p>Preços: de <a href="http://www1.folha.uol.com.br/folha/informatica/ult124u448784.shtml" onclick="javascript:urchinTracker('/outbound/article/www1.folha.uol.com.br');">1000 a 3000 na Claro</a>, e de 899 a 2199 na <a href="http://www1.folha.uol.com.br/folha/informatica/ult124u448974.shtml" onclick="javascript:urchinTracker('/outbound/article/www1.folha.uol.com.br');">Vivo</a>.</p>
<p>Acho que não será agora que terei meu iPhone. Muito caro!</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=oG73L"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=oG73L" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=7jVnL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=7jVnL" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/403236008" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/09/25/iphone-precos-definidos/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/09/25/iphone-precos-definidos/</feedburner:origLink></item>
		<item>
		<title>iPhone no Brasil tem data marcada</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/402755196/</link>
		<comments>http://log4dev.com/2008/09/25/iphone-no-brasil-tem-data-marcada/#comments</comments>
		<pubDate>Thu, 25 Sep 2008 12:26:34 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Produto]]></category>

		<category><![CDATA[Apple]]></category>

		<category><![CDATA[iPhone]]></category>

		<category><![CDATA[Mercado]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/09/25/iphone-no-brasil-tem-data-marcada/</guid>
		<description><![CDATA[Rápido e rasteiro: o iPhone, segundo fontes próximas às negociações, agora tem data oficial para ser lançado no Brasil, segundo o site MacWorld Brasil!
Será no dia 26 de setembro, em evento conjunto da Apple, Claro e Vivo. O telefone será lançado também na Turquia neste dia.
Mas a pergunta quer não quer calar: quanto vai custar [...]]]></description>
			<content:encoded><![CDATA[<p>Rápido e rasteiro: o <strong>iPhone</strong>, segundo fontes próximas às negociações, agora tem data oficial para ser lançado no Brasil, segundo o site <a href="http://www.macworldbrasil.com.br/noticias/2008/09/16/lancamento-do-iphone-3g-no-brasil-esta-marcado-para-26-de-setembro/" onclick="javascript:urchinTracker('/outbound/article/www.macworldbrasil.com.br');">MacWorld Brasil</a>!</p>
<p>Será no dia <strong>26 de setembro,</strong> em evento conjunto da <strong>Apple</strong>, <strong>Claro</strong> e <strong>Vivo</strong>. O telefone será lançado também na Turquia neste dia.</p>
<p>Mas a pergunta quer não quer calar: quanto vai custar o bendito?! Isso nem Jobs deve saber&#8230;&#8230;</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=XSQxL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=XSQxL" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=QXzeL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=QXzeL" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/402755196" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/09/25/iphone-no-brasil-tem-data-marcada/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/09/25/iphone-no-brasil-tem-data-marcada/</feedburner:origLink></item>
		<item>
		<title>Rails Summit Latin America</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/397424133/</link>
		<comments>http://log4dev.com/2008/09/19/rails-summit-latin-america/#comments</comments>
		<pubDate>Fri, 19 Sep 2008 18:15:03 +0000</pubDate>
		<dc:creator>Thiago</dc:creator>
		
		<category><![CDATA[Formação]]></category>

		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Rails]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/09/19/rails-summit-latin-america/</guid>
		<description><![CDATA[Pra quem se interessa por Ruby e em particular por Ruby on Rails (RoR), o Rails Summit Latin America eh uma oportunidade imperdível. O evento vai acontecer nos dias 15 e 16 de outubro em São Paulo, e conta com a presença de diversos palestrantes internacionais. É também uma ótima chance de entrar em contato [...]]]></description>
			<content:encoded><![CDATA[<p>Pra quem se interessa por Ruby e em particular por Ruby on Rails (RoR), o <a href="http://www.locaweb.com.br/railssummit/" onclick="javascript:urchinTracker('/outbound/article/www.locaweb.com.br');">Rails Summit Latin America</a> eh uma oportunidade imperdível. O evento vai acontecer nos dias 15 e 16 de outubro em São Paulo, e conta com a presença de diversos palestrantes internacionais. É também uma ótima chance de entrar em contato com a comunidade brasileira e latino americana de RoR e Ruby.</p>
<p>Essa foi a parte propaganda para o evento, agora vem a propaganda para mim. Meu irmão comprou o ingresso para o evento quando eles estavam com uma promoção para ingressos adiantados, e pagou 300 reais. Depois eles criaram uma promoção de 100 reais para estudante. Como a organização disse que não tem como devolver o dinheiro, eles deram 3 opções pra quem comprou antecipado mas tem direito a estudante:</p>
<ul>
<li>ele pode transferir o ingresso antigo para alguma outra pessoa e comprar um de estudante;</li>
<li>ele pode dividir o ingresso dele com mais 2 estudantes; ou</li>
<li>ele pode desfrutar de um credito de 200 reais em serviços de um patrocinador do evento.</li>
</ul>
<p>Eu não entendo muito bem essa historia de &#8220;não tem como devolver o dinheiro&#8221;. Pelo menos neste ano ainda não tem CPMF, então bastaria eles colocarem de volta 200 reais na conta, ou devolver no cartão de credito, ou mesmo entregar em mãos. Mas de qualquer forma, pelo menos eles estao tentando ressarcir de alguma forma.</p>
<p>O problema é que meu irmão não conhece ninguém que esteja interessado, e também não está interessado em nenhum produto do patrocinador. Então, se alguém se interessar e quiser dividir a entrada ou comprar a entrada pelo preço antecipado, entre em contato comigo e a gente tenta ajeitar isso.</p>
<p>Vale lembrar que o preço (mesmo o de 300 reais) é muito barato pelo retorno que traz: palestras de altíssima qualidade, contato com gente interessante e ainda contando com almoço e coffee breaks. Queria eu estar no Brasil nesses dias!</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=qpvlL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=qpvlL" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=AVEML"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=AVEML" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/397424133" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/09/19/rails-summit-latin-america/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/09/19/rails-summit-latin-america/</feedburner:origLink></item>
		<item>
		<title>Configuração de teclas no Emacs do Mac</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/393772492/</link>
		<comments>http://log4dev.com/2008/09/15/configuracao-de-teclas-no-emacs-do-mac/#comments</comments>
		<pubDate>Tue, 16 Sep 2008 02:26:00 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Ferramentas]]></category>

		<category><![CDATA[Emacs]]></category>

		<category><![CDATA[Mac]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/09/15/configuracao-de-teclas-no-emacs-do-mac/</guid>
		<description><![CDATA[O trio Mac + Python + Emacs tem me ajudado muito a ser produtivo e a desenvolver meus projetos. O Aquamacs é um porte nativo do Emacs para a o OS X que consegue misturar bastante bem o poder do Emacs com elementos clássicos da interface Mac, como atalhos e afins. Mas para que as [...]]]></description>
			<content:encoded><![CDATA[<p>O trio Mac + Python + Emacs tem me ajudado muito a ser produtivo e a desenvolver meus projetos. O <a href="http://aquamacs.org/" onclick="javascript:urchinTracker('/outbound/article/aquamacs.org');">Aquamacs</a> é um porte nativo do Emacs para a o OS X que consegue misturar bastante bem o poder do Emacs com elementos clássicos da interface Mac, como atalhos e afins. Mas para que as coisas funcionem corretamente, alguns ajustes específicos são necessários, como em relação tecla Alt+Option.</p>
<p>Usuários do Emacs sabem que esta tecla é o atalho para o Meta, base para a maioria dos comandos. Mas é também, infelizmente, a tecla necessária para se escrever a maioria dos acentos no teclado Mac: Alt+e+e = é, Alt+c = ç, Alt+n+a = ã, e assim por diante.  Aliás, isto apenas corrobora o fato de que nada é perfeito no mundo.</p>
<p>Por default, o Emacs processa o Alt como Meta. Portanto, enquanto a Apple não lança um teclado decente, devemos abdicar dos acentos?</p>
<p>Não! O povo do Aquamacs ofereceu uma ótima solução. Os comandos</p>
<p><em>(setq mac-option-modifier nil)<br />
(setq mac-pass-option-to-system t)</em></p>
<p>dentro do arquivo .emacs forçam o editor a repassar o controle da tecla Alt para o sistema operacional, reestabelecendo a funcionalidade do acento. Mas desta forma, temos que usar o pouco ergonômico ESC para obter o Meta?</p>
<p>Também não! É possível mapear outras teclas para esta função. Uma possibilidade é o Command (tecla da maçã), através do comando</p>
<p><em>(setq mac-command-modifier &#8216;meta)</em><br />
que inclusive apresenta a vantagem de ser ao lado da tecla Alt. Por outro lado, bloqueia o acesso a atalhos específicos do Mac, como Command + S. Isso talvez não seja nenhum problema para os mais puristas do sistema do Stallman.</p>
<p>Outra solução é mapear a tecla Fn (function) para assumir a função de Meta, através do comando</p>
<p><em>(setq mac-function-modifier &#8216;meta)</em></p>
<p>Esta foi a minha solução favorita e definitiva!</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=QfFrL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=QfFrL" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=A91yL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=A91yL" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/393772492" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/09/15/configuracao-de-teclas-no-emacs-do-mac/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/09/15/configuracao-de-teclas-no-emacs-do-mac/</feedburner:origLink></item>
		<item>
		<title>Feedback</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/383255821/</link>
		<comments>http://log4dev.com/2008/09/04/feedback/#comments</comments>
		<pubDate>Thu, 04 Sep 2008 13:38:34 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Opinião]]></category>

		<category><![CDATA[Ferramentas]]></category>

		<category><![CDATA[job4dev]]></category>

		<category><![CDATA[Mercado]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/09/04/feedback/</guid>
		<description><![CDATA[Email enviado por Daniel Cassiano (http://danielcassiano.net/) na segunda-feira, 2 de Setembro:
 Olá!
Gostaria de levar a conhecimento de vocês que consegui meu trabalho através do job4dev!
Na verdade isso já tem 3 meses e meio. Estava para fazer isso há um tempo, mas sempre algo impedia.
Hoje estou aqui pra expressar minha gratidão a vocês! Muito obrigado!
Empresa que [...]]]></description>
			<content:encoded><![CDATA[<p>Email enviado por Daniel Cassiano (<a href="http://danielcassiano.net/" onclick="javascript:urchinTracker('/outbound/article/danielcassiano.net');">http://danielcassiano.net/</a>) na segunda-feira, 2 de Setembro:</p>
<blockquote><p> Olá!</p>
<p>Gostaria de levar a conhecimento de vocês que consegui meu trabalho através do job4dev!<br />
Na verdade isso já tem 3 meses e meio. Estava para fazer isso há um tempo, mas sempre algo impedia.<br />
Hoje estou aqui pra expressar minha gratidão a vocês! Muito obrigado!</p>
<p>Empresa que me contratou: Apontador.com (atualmente Apontador MapLink)</p>
<p>Parabés por essa iniciativa.<br />
Vou publicar a gif de vocês no meu site.</p>
<p>Abs!</p></blockquote>
<p>Não sei quanto a vocês, mas este tipo de feedback só faz aumentar a minha motivação e a minha convicção de que este projeto está no caminho certo.</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=kKyx1L"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=kKyx1L" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=qc1buL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=qc1buL" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/383255821" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/09/04/feedback/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/09/04/feedback/</feedburner:origLink></item>
		<item>
		<title>Chrome, primeiras impressões</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/381711568/</link>
		<comments>http://log4dev.com/2008/09/02/chrome-primeiras-impressoes/#comments</comments>
		<pubDate>Tue, 02 Sep 2008 21:13:55 +0000</pubDate>
		<dc:creator>Miguel</dc:creator>
		
		<category><![CDATA[Notícias]]></category>

		<category><![CDATA[Opinião]]></category>

		<category><![CDATA[Produto]]></category>

		<category><![CDATA[Chrome]]></category>

		<category><![CDATA[Ferramentas]]></category>

		<category><![CDATA[Google]]></category>

		<category><![CDATA[Web]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/09/02/chrome-primeiras-impressoes/</guid>
		<description><![CDATA[Por Patrice Lamiral
Está sendo uma semana agitada para o twitteiros de plantão.
Primeiro veio o blip.fm que é uma rádio customizada que você pode integrar em diversas plataformas de microblogging como twitter, pownce e Jaiku. Por essa eu passei ileso.
Agora veio o Chrome, o navegador do Google. Aí não teve jeito, vi a comoção geral das [...]]]></description>
			<content:encoded><![CDATA[<p><strong>Por Patrice Lamiral</strong></p>
<p>Está sendo uma semana agitada para o twitteiros de plantão.</p>
<p>Primeiro veio o <a href="http://blip.fm/" target="_blank" onclick="javascript:urchinTracker('/outbound/article/blip.fm');">blip.fm</a> que é uma rádio customizada que você pode integrar em diversas plataformas de microblogging como twitter, pownce e Jaiku. Por essa eu passei ileso.</p>
<p>Agora veio o Chrome, o navegador do Google. Aí não teve jeito, vi a comoção geral das pessoas no twitter (procure pela tag #chrome no <a href="http://summize.com/" target="_blank" onclick="javascript:urchinTracker('/outbound/article/summize.com');">summize.com</a> e entenda) e instalei a novidade. As primeiras impressões são positivas, mais por ser do google do que por ser bom mesmo, até proque não deu tempo de avaliar os recursos disponíveis. Mas em linhas gerais gostei do melhor aproveitamento da tela - a navegação é fullscreen por default -, gostei dos atalhos de páginas favoritas para desktop, aprovei a intolerância para com pop-ups e achei ótimo que eles tenham mantido uma estrutura semelhante à do firefox.</p>
<p>A pergunta que não quer calar: vou trocar o Firefox pelo Chrome? Por enquanto não porque ainda não existem os plug-ins para twitters e delicious da vida. Mas é uma questão de tempo. O Google é o midas digital, tudo que ele toca (ou quase tudo) vira ouro.</p>
<p>Aposto que em breve eles lançarão um banco.</p>
<p><strong><span dir="ltr" id=":zb">[Patrice Lamiral</span><span dir="ltr" id=":zb">, além de leitor do log4dev,</span><span dir="ltr" id=":zb"> é marketeiro, entusiasta de novas tecnologias e mídias digitais e baixou o Chrome antes que muito computeiro por aí&#8230;</span></strong> ]</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=gT2ODL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=gT2ODL" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=h1q7CL"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=h1q7CL" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/381711568" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/09/02/chrome-primeiras-impressoes/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/09/02/chrome-primeiras-impressoes/</feedburner:origLink></item>
		<item>
		<title>Bizarro… mas muito útil!</title>
		<link>http://feeds.feedburner.com/~r/log4dev/xml/~3/376697693/</link>
		<comments>http://log4dev.com/2008/08/27/bizarro-mas-muito-util/#comments</comments>
		<pubDate>Thu, 28 Aug 2008 02:01:14 +0000</pubDate>
		<dc:creator>Leonardo</dc:creator>
		
		<category><![CDATA[Desenvolvimento]]></category>

		<category><![CDATA[bizarro]]></category>

		<category><![CDATA[C]]></category>

		<category><![CDATA[macros]]></category>

		<guid isPermaLink="false">http://log4dev.com/2008/08/27/bizarro-mas-muito-util/</guid>
		<description><![CDATA[O artigo do Miguel sobre perólas do mundo Java me fez lembrar de um trecho de código com o qual me deparei há um tempo atrás que me parecia também muito bizarro&#8230; até eu sacar um pouco depois a imensa utilidade dele!
O código, em linguagem C, era algo como o seguinte:
do {
  __alguma_coisa;
} while [...]]]></description>
			<content:encoded><![CDATA[<p>O artigo do Miguel sobre <a href="http://log4dev.com/2008/08/10/perolas-do-mundo-java/" >perólas do mundo Java</a> me fez lembrar de um trecho de código com o qual me deparei há um tempo atrás que me parecia também muito bizarro&#8230; até eu sacar um pouco depois a imensa utilidade dele!</p>
<p>O código, em linguagem C, era algo como o seguinte:</p>
<pre>do {
  __alguma_coisa;
} while (false);</pre>
<p>Em princípio fazer uma construção de laço para executar algo apenas uma vez parece algo bem bizarro, não?! Diria que é quase um primo-irmão do <code>if (liberado==true)</code>. Foi exatamente o que eu achei. Mas colocando esta construção dentro do contexto em que eu a achei eu consegui ver (depois de alguma pesquisa, é claro) que ela é extremamente útil em alguns casos.</p>
<p>A primeira vez que eu me deparei com esta construção eu estava analisando o código-fonte do <a href="http://www.gnu.org/software/chess/" onclick="javascript:urchinTracker('/outbound/article/www.gnu.org');">GNUChess</a>, um jogo de xadrez de código livre. Como eu sei que o pessoal que escreve código livre algumas vezes utiliza umas construções bem diferentes do que normalmente estamos acostumados, resolvi investigar o porquê deles estarem utilizando esta construção. Afinal de contas, se este código é livre e várias pessoas já devem tê-lo revisado, não havia motivo para um laço aparentemente tão inútil estar lá sem alguma utilidade verdadeira, não é mesmo?!</p>
<p>E foi só pesquisar um pouco sobre o assunto para enteder melhor o que estava acontecendo. As construções como a acima só apareciam em definições de macros. Nunca em código &#8220;normal&#8221;. Para quem talvez não tenha muita familiaridade com <a href="http://en.wikipedia.org/wiki/Macro_(computer_science)#Text_substitution_macros" onclick="javascript:urchinTracker('/outbound/article/en.wikipedia.org');">macros em C</a>, elas são basicamente códigos que você define e que serão literalmente expandidos pelo compilador onde seu identificador aparecer no código. Ou seja, um código assim:</p>
<pre>#define macro_exemplo printf("Macro de exemplo!\n");
int main(void) {
  macro_exemplo
  return 0;
}</pre>
<p>seria entendido pelo compilador, após o processamento das macros, da seguinte forma:</p>
<pre>int main(void) {
  printf("Macro de exemplo!\n");
  return 0;
}</pre>
<p>Ou seja, o preprocessador de código do compilador substitui a referência à <code>macro_exemplo</code> pela sua definição literal. No caso do nosso código bizarro, teríamos que definir a macro da seguinte forma:</p>
<pre>#define macro_exemplo2 do { __alguma_coisa; } while (false);</pre>
<p>ou ainda:</p>
<pre>#define macro_exemplo3 do { \
                         __alguma_coisa; \
                       } while (false);</pre>
<p>Note que uma macro deve ser definida sem quebras de linhas ou com quebras de linhas sinalizadas pelo caracter de escape barra invertida (&#8217;\').</p>
<p>Mas, ainda assim, não haveria motivo para o laço na minha macro, certo? Bom, se você pensar na macro como um código por si só, talvez isto esteja certo, mas não podemos esquecer que este código será copiado literalmente para algum outro lugar sempre que o identificador da macro for referenciado pelo programa. E muitas vezes não queremos fazer macros simples como as que eu mostrei no meu exemplo. Por exemplo, podemos querer fazer algo mais complexo como o seguinte:</p>
<pre>#define IMPRIME_ESPACOS(n) for (int j = 0; j &lt; n; j++) printf(" ");
#define ROTULO(rot) printf("L%d:", rot); do { \
          int n = numeroDigitos(rot); \
          IMPRIME_ESPACOS(6 - (n + 2))\
} while (false);</pre>
<p>A macro <code>IMPRIME_ESPACOS(n)</code> imprime uma quantidade de espaços em branco representadas pelo &#8220;argumento&#8221; n. Estou usando argumento entre aspas porque o argumento de uma macro em C se comporta de maneira diferente de um argumento de função, já que não há checagem de tipo e sim uma simples substituição do valor passado como argumento da macro nas suas referências dentro da própria macro. Já a macro <code>ROTULO(rot)</code> recebe como &#8220;argumento&#8221; um rótulo e imprime <code>Lrot</code> seguido de um numero de espaços de tal forma que todas as linhas que chamarem a macro <code>ROTULO(rot)</code> estarão identadas na mesma posição (desde que o rótulo tenha menos de 6 caracteres, que era o limite utilizado no programa a partir do qual tirei o código de exemplo).</p>
<p>Alguém certamente já bateu o olho no código acima e deve ter dito: poxa, eu poderia chamar a função<br />
<code>numeroDigitos(rot)</code> dentro de <code>IMPRIME_ESPACOS</code> na definição da macro <code>ROTULO</code>. Não podemos nos esquecer no entanto que macros não são chamadas de função e que onde se lê <code>IMPRIME_ESPACOS</code> em <code>ROTULO</code> dever-se-ia ler na verdade a definição de <code>IMPRIME_ESPACOS</code>. Neste caso, se passássemos uma chamada de <code>numeroDigitos</code> como &#8220;argumento&#8221; de <code>IMPRIME_ESPACOS</code>, a função <code>numeroDigitos</code> seria chamada dentro do loop definido em <code>IMPRIME_ESPACOS</code> sempre que a condição de parada do loop fosse ser calculada. Ou seja, teríamos um número excessivo e desnecessário de chamadas a <code>numeroDigitos</code>. Para solucionar este eventual problema, decidi criar uma variavel para armazenar o valor da chamada de <code>numeroDigitos</code> e passar esta variavel como argumento para <code>IMPRIME_ESPACOS</code>. O problema é que dependendo de onde este código for ser substituído pode não ser permitido ter declarações de variáveis.</p>
<p>Neste último caso (e em muitos outros), o código mostrado no início deste post, por mais bizarro que possa parecer a primeira vista, pode ser a solução, pois o uso do <code> do { ... } while (false);</code> torna possível a criação de um contexto local dentro das chaves do falso loop na macro. Dentro deste contexto é possível criar-se quantas variáveis se queira ou, por exemplo, encadear comandos dentro de uma macro que não ficarão perdidos se esta macro for utilizada dentro de um if-else.</p>
<p>Ah, e se alguém ficou curioso, procure na Internet: vocês verão muitos outros usos do do-while (false). Sinceramente, muitos deles, na minha opinião são dispensáveis e só servem para complicar código que poderia ser escrito de outra forma. E, pra falar a verdade, a única construção que eu já achei em códigos livres foi esta que eu cito aqui, dentro de macros. É preciso ter dicernimento na hora de usar este tipo de construção. Aliás, para falar a verdade, mesmo este caso que eu descrevi aqui, que eu acho interessante e útil eu só usária em últimos casos em códigos profissionais.</p>
<div class="feedflare">
<a href="http://feeds.feedburner.com/~f/log4dev/xml?a=WU0gWK"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=WU0gWK" border="0"></img></a> <a href="http://feeds.feedburner.com/~f/log4dev/xml?a=05IewK"><img src="http://feeds.feedburner.com/~f/log4dev/xml?i=05IewK" border="0"></img></a>
</div><img src="http://feeds.feedburner.com/~r/log4dev/xml/~4/376697693" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://log4dev.com/2008/08/27/bizarro-mas-muito-util/feed/</wfw:commentRss>
		<feedburner:origLink>http://log4dev.com/2008/08/27/bizarro-mas-muito-util/</feedburner:origLink></item>
	<lastBuildDate>Mon, 01 Dec 2008 00:00:00 -0600</lastBuildDate></channel>
</rss>
