<?xml version="1.0" encoding="UTF-8"?><!-- generator="wordpress.com" -->
<rss version="2.0"
	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/"
	>

<channel>
	<title>egrep &amp;laquo; WordPress.com Tag Feed</title>
	<link>http://en.wordpress.com/tag/egrep/</link>
	<description>Feed of posts on WordPress.com tagged "egrep"</description>
	<pubDate>Mon, 07 Dec 2009 20:00:04 +0000</pubDate>

	<generator>http://en.wordpress.com/tags/</generator>
	<language>en</language>

<item>
<title><![CDATA[Adding timestamps in JMAP log]]></title>
<link>http://qants.wordpress.com/2009/12/02/adding-timestamps-in-jmap-log/</link>
<pubDate>Wed, 02 Dec 2009 17:08:17 +0000</pubDate>
<dc:creator>Alex Ersenie</dc:creator>
<guid>http://qants.wordpress.com/2009/12/02/adding-timestamps-in-jmap-log/</guid>
<description><![CDATA[As i was discussing in a previous article of mine, i use jmap to export heap statistics on a periodi]]></description>
<content:encoded><![CDATA[<div class='snap_preview'><p>As i was discussing in a <a href="http://qants.wordpress.com/2009/10/09/prepare-jmap-output-for-data-import-transform-to-csv/">previous article of mine</a>, i use jmap to export heap statistics on a periodical basis, while i run my performance tests. The biggest disadvantage of jmap is that it does not have any timestamp logging enabled.</p>
<p>Today i found myself badly needing a timestamp, in order to better track and isolate my &#8220;heap loosers&#8221; <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' />  So there i was, back to regular expressions, on the fly text editing, sed, awk, greps&#8230;all those beloved friends.</p>
<p>Well, in the end, i managed to figure something out, and it looks like this:</p>
<blockquote><p><span style="color:#993366;">JMAP_TIMESTAMP=`date +%H-%M-%S`<br />
                ssh ${DOMAIN_SERVER} &#8220;sudo -u glassfish /bin/bash -c &#8216;${JAVA_BIN}jmap -histo ${glassfish_pid}&#8217;&#8221; &#124; egrep  -i -e &#8216;\[[I,B,C]+&#8217;  -e &#8216;java.util.Hash&#8217; -e &#8216;java.util.Vector&#8217; -e &#8216;Klass&#8217; &#124; sed &#8216;/[0-9]/s/$/&#8217;,&#8221;${JMAP_TIMESTAMP}&#8221;&#8216;/&#8217; &#62;&#62; /tmp/filtered.log</span></p></blockquote>
<p>Where:</p>
<p>JMAP_TIMESTAMP is the time of the system, in the HH-MM-SS format, and is used as a variable when replacing on the fly</p>
<p>DOMAIN_SERVER is the server name where the Glassfish Server is running</p>
<p>JAVA_BIN is a variable containing the path to the JAVA BIN folder on the server</p>
<p>glassfish_pid is a variable that contains the pid of the running application server</p>
<p>The piece of code above, will strip the white spaces, the &#8220;:&#8221;, and will add the timestamps at the end of each line.</p>
<p>I myself run this piece of code in a while loop every 5 seconds, and use the &#8220;filtered.log&#8221; file for appending the information that i will later use for data importing and transformation</p>
<p>Hope it will be of use to you guys</p>
<p>Cheers, gluhwein and Christmas Market is waiting for me <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_biggrin.gif' alt=':D' class='wp-smiley' /> </p>
<p>Alex</p>
</div>]]></content:encoded>
</item>
<item>
<title><![CDATA[grep, egrep - tiện ích rất tuyệt vời trong unix  ]]></title>
<link>http://cauhoi.wordpress.com/2009/11/30/grep-egrep-ti%e1%bb%87n-ich-r%e1%ba%a5t-tuy%e1%bb%87t-v%e1%bb%9di-trong-unix/</link>
<pubDate>Mon, 30 Nov 2009 17:19:01 +0000</pubDate>
<dc:creator>docphong</dc:creator>
<guid>http://cauhoi.wordpress.com/2009/11/30/grep-egrep-ti%e1%bb%87n-ich-r%e1%ba%a5t-tuy%e1%bb%87t-v%e1%bb%9di-trong-unix/</guid>
<description><![CDATA[Tiếp theo series filter trong unix, lần này tôi muốn đề cập tới một filter nữa rất hữu dụng và cũng ]]></description>
<content:encoded><![CDATA[<div class='snap_preview'><p>Tiếp theo series filter trong unix, lần này tôi muốn đề cập tới một filter nữa rất hữu dụng và cũng rất thông dụng, đó là grep và egrep &#8211; một mở rộng của nó (fgrep bạn có thể tự tìm hiểu thêm). Trước hết, 2 filter trên dùng để làm gì ? Chúng được dùng để lọc ra các dòng thỏa mãn một mẫu (partern) mà bạn chỉ định, ví dụ như số điện thoại, địa chỉ IP, tên, &#8230;</p>
<p><!--more--></p>
<p>Hai filter này thực ra có thể đồng nhất được, tức là bạn có thể dùng egrep nếu thêm tùy chọn -e vào trong câu lệnh grep. Cấu trúc lệnh grep: </p>
<blockquote><p>grep [OPTIONS] PATTERN [FILE...]</p></blockquote>
<p>Các option thông dụng, bạn có thể gặp và sử dụng:</p>
<ul>
<li>-f : thay vì việc bạn chỉ ra một partern dài, bạn có thể chỉ ra file chứa partern đó</li>
<li>-i : bỏ qua mọi khác biệt về chữ hoa/thường giữa partern và nội dung trong file đầu vào</li>
<li>-v : thực hiện tìm các dòng không chứa partern được đưa ra</li>
<li>-w : chỉ tìm những dòng mà có từ khớp toàn bộ với mẫu tìm kiếm</li>
<li>-x : tìm dòng mà toàn bộ dòng khớp với mẫu tìm kiếm </li>
<li>-c (&#8211;count ): Thay vì liệt kê các dòng khớp, nó cho ra số dòng khớp, nếu sử dụng cùng với tùy chọn -v thì nó sẽ đếm số dòng không khớp</li>
<li>-m NUM hoặc &#8211;max-count=NUM : Khi khớp được NUM dòng, nó sẽ không tìm tiếp trong file nữa</li>
<li>-q hoặc &#8211;quiet, &#8211;silent : Không in ra bất cứ thứ gì ở standard output, trả về 0 khi match được bất cứ môt kết quả nào. Khi bạn chạy một shell thì điều này sẽ cần dùng đến. Nếu không thu được kết quả nào, sẽ trả về một lỗi error (có thể sẽ được gửi tới stder <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_biggrin.gif' alt=':D' class='wp-smiley' /> ).</li>
<li>-H hoặc &#8211;with-filename : in các dòng match cùng với tên file chứa nó (trong trường hợp tìm trên nhiều file). Tùy chọn này là mặc định, bạn không cần chỉ ra nó.</li>
<li>-h, hoặc &#8211;no-filename : không thêm tên các file ứng với các dòng match.</li>
</ul>
</div>]]></content:encoded>
</item>
<item>
<title><![CDATA[[grep] grep, egrep and fgrep ]]></title>
<link>http://nixtricks.wordpress.com/2009/09/26/grep-grep-egrep-and-fgrep/</link>
<pubDate>Sat, 26 Sep 2009 06:44:31 +0000</pubDate>
<dc:creator>kousik</dc:creator>
<guid>http://nixtricks.wordpress.com/2009/09/26/grep-grep-egrep-and-fgrep/</guid>
<description><![CDATA[I always get confused about various flavors of grep. Here&#8217;s a summary to shine some light: (ma]]></description>
<content:encoded><![CDATA[<div class='snap_preview'><p>I always get confused about various flavors of <code>grep</code>. Here&#8217;s a summary to shine some light: (<code>man grep</code>  to know more!)</p>
<ul>
<li> <code>egrep</code> or <code>grep -E</code> (in linux only) is extended grep where additional regular expression metacharacters have been added like <code>+, ?, &#124; and ()</code></li>
<li><code>fgrep</code> or <code>grep -F  </code> (in linux only) is fixed or fast grep and behaves as grep but does not recognize any regular expression metacharacters as being special.</li>
</ul>
</div>]]></content:encoded>
</item>
<item>
<title><![CDATA[[grep] AND, OR, and "these" but NOT "those"]]></title>
<link>http://nixtricks.wordpress.com/2009/09/25/grep-and-or-these-but-not-those/</link>
<pubDate>Sat, 26 Sep 2009 01:30:43 +0000</pubDate>
<dc:creator>kousik</dc:creator>
<guid>http://nixtricks.wordpress.com/2009/09/25/grep-and-or-these-but-not-those/</guid>
<description><![CDATA[For grepping line-by-line in a file filename, I often find these very useful Match pattern1 OR patte]]></description>
<content:encoded><![CDATA[<div class='snap_preview'><p>For <em>grepping</em> line-by-line in a file <em>filename</em>, I often find these very useful</p>
<p><strong>Match <code>pattern1</code> OR<code> pattern2 in the same line</code>:</strong><br />
<code> $ grep -E 'pattern1&#124;pattern2' </code><em>filename</em></p>
<p><strong>Match <code>pattern1</code> AND <code>pattern2 in the same line</code>:</strong><br />
<code> $ grep -E 'pattern1.*pattern2' </code><em>filename</em><br />
The above command searches for <code>pattern1</code> followed by <code>pattern2</code>. If the order does not matter or you want to search them in either order, then use the follwoing<br />
<code> $ grep -E 'pattern1.*pattern2&#124;pattern2.*pattern1' </code><em>filename</em><br />
The pipe enables the OR search which we saw earlier. Another option for this situation (i.e., AND search when the order is not important):<br />
<code> $ grep -E 'pattern1' &#124; grep -E 'pattern2'</code><br />
which basically greps the STDOUT of the first grep.</p>
<p><strong>Match <code>pattern1</code> AND<code> pattern2</code>, but NOT <code>pattern3</code> in the same line:</strong><br />
<code> </code><code> $ grep -E 'pattern1.*pattern2' </code><em>filename</em> <code>&#124; grep -Ev 'pattern3'</code><br />
when the order of the first two patterns is important. When that order is NOT important:<br />
<code> $ grep -E 'pattern1'<em> filename</em> &#124; grep -E 'pattern2' &#124; grep -Ev 'pattern3'</code></p>
<p><strong>Match <code>pattern1</code> OR <code>pattern2</code>, but NOT <code>pattern3</code> in the same line:</strong><br />
<code> </code><code> $ grep -E 'pattern1&#124;pattern2' </code><em>filename</em> <code>&#124; grep -Ev 'pattern3'</code></p>
<p><strong>N.B.</strong> (1) <code> grep -E</code> may be replaced by <code> egrep</code>.  I used <code> grep -E</code> everywhere in this post assuming a general case of regular expressions as patterns. Lowercase <code>-e</code> is also used for regex, but this is more &#8220;basic&#8221; than <code>-E</code> which supports &#8220;extended&#8221; regex, e.g. regular expression metacharacters like +, ?, &#124; and ().  (2) The <code> -v</code> flag is for non-matching grep.</p>
</div>]]></content:encoded>
</item>
<item>
<title><![CDATA[egrep: la última ocurrencia]]></title>
<link>http://orugaelectronica.wordpress.com/2008/09/18/egrep-la-ultima-ocurrencia/</link>
<pubDate>Thu, 18 Sep 2008 04:17:56 +0000</pubDate>
<dc:creator>jmrepetti</dc:creator>
<guid>http://orugaelectronica.wordpress.com/2008/09/18/egrep-la-ultima-ocurrencia/</guid>
<description><![CDATA[Dado un nombre de archivo, o una parte del mismo, encontar en un listado de archivos, con su path re]]></description>
<content:encoded><![CDATA[<div class='snap_preview'><p>Dado un nombre de archivo, o una parte del mismo, encontar en un listado de archivos, con su path relativo(o absoluto), la linea o lineas que coincidan, pero solo en la parte de nombre del archivo y no en el nombre del directorio.</p>
<p>Genero un listado de archivos que me interesan, digamos una especie de indice. Para asegurame que la salida del comando <strong>find</strong> sólo contenga archivos, le paso el parámetro <em>-type f</em>. En mi caso, también quiero evitar mostar en la salida de <strong>find</strong> los archivos del directorio .git(o .svn), entonces entubo el comando <strong>egrep</strong> con la expresión <em>-v &#8216;.git&#124;.svn&#8217;</em>. El parámetro <em>-v</em> invierte el comportamiento normal de <strong>egrep</strong>. Esto es, en lugar de filtrar y dejar pasar lo que coincide según la expresión regular, deja pasar todo menos lo que coincide.</p>
<p>Bien, creo el indice de archivos:</p>
<p><code>fellini:~/dev/proyecto_millonario $ find . -type f &#124; egrep -v '.git&#124;.svn' &#62; lista_de_archivos</code></p>
<p>Ahora para obtener el path, en este caso relativo, del archivo que estoy buscando uso este comando, donde <strong>cadena</strong> es parte del nombre del archivo:</p>
<p><code>fellini:~/dev/proyecto_millonario $ cat lista_de_archivos &#124; egrep -i '/.*<strong>cadena</strong>[^/]+$'</code></p>
</div>]]></content:encoded>
</item>
<item>
<title><![CDATA[give me a shell]]></title>
<link>http://netcrash.wordpress.com/2008/05/16/give-me-a-shell/</link>
<pubDate>Fri, 16 May 2008 02:46:12 +0000</pubDate>
<dc:creator>Fernando André</dc:creator>
<guid>http://netcrash.wordpress.com/2008/05/16/give-me-a-shell/</guid>
<description><![CDATA[ls -l  | awk &#8216;{ system(&#8220;chown -R &#8220;$3&#8243; &#8220;$8) }&#8217; //cuidado com dire]]></description>
<content:encoded><![CDATA[<div class='snap_preview'><p>ls -l  &#124; awk &#8216;{ system(&#8220;chown -R &#8220;$3&#8243; &#8220;$8) }&#8217;</p>
<p>//cuidado com directorios que contenham espaços doens&#8217;t work with spaces ;</p>
<p>find /home/ -uid 0 -exec ls -l \{\} \;</p>
<p>fgrep &#8216;gold&#8217; /var/log/ -R &#124; grep -i something</p>
<p>or regexp style search<br />
egrep &#8216;(err&#124;fail&#124;warning)&#8217; /var/log/* &#62; `date +%F`.txt</p>
<p>ls -l  &#124; sed -e &#8217;s/andre/netcrash/gi&#8217;</p>
<p>#!/usr/bin/perl</p>
<p>print &#8220;hello\n&#8221;;<br />
$dir=&#8221;/home/andre&#8221;;<br />
if ( (!(-d $dir.&#8221;/Maildir&#8221;)) ){<br />
`/usr/bin/maildirmake.maildrop $dir&#8221;/Maildir&#8221;`;</p>
<p>}</p>
<p>bash<br />
[03:42:08]andre@garden:~$ for i in `seq 10`; do echo $i ; done;</p>
<p>Haven&#8217;t been using cut that mutch but, also a good weapon of choice.</p>
<p><strong>Simple things that evolve to more complex tools <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_biggrin.gif' alt=':D' class='wp-smiley' /> </strong></p>
</div>]]></content:encoded>
</item>
<item>
<title><![CDATA[Papo de Botequim - Parte 2]]></title>
<link>http://jneves.wordpress.com/2008/03/05/papo-de-botequim-parte-2-2/</link>
<pubDate>Wed, 05 Mar 2008 16:38:01 +0000</pubDate>
<dc:creator>jneves</dc:creator>
<guid>http://jneves.wordpress.com/2008/03/05/papo-de-botequim-parte-2-2/</guid>
<description><![CDATA[Eu fico com o grep, você com a gripe A família grep Vamos Montar uma &#8220;cdteca&#8221; Passando p]]></description>
<content:encoded><![CDATA[<div class='snap_preview'><div class="twikiToc">
<ul>
<li> <a href="http://twiki.softwarelivre.org/bin/view/TWikiBar/TWikiBarPapo002#Eu_fico_com_o_grep_voc%C3%AA_com_a_gr"> Eu fico com o grep, você com a gripe</a>
<ul>
<li> <a href="http://twiki.softwarelivre.org/bin/view/TWikiBar/TWikiBarPapo002#A_fam%C3%ADlia_grep"> A família grep</a></li>
</ul>
</li>
<li> <a href="http://twiki.softwarelivre.org/bin/view/TWikiBar/TWikiBarPapo002#Vamos_Montar_uma_cdteca"> Vamos Montar uma &#8220;cdteca&#8221;</a>
<ul>
<li> <a href="http://twiki.softwarelivre.org/bin/view/TWikiBar/TWikiBarPapo002#Passando_par%C3%A2metros"> Passando parâmetros</a></li>
<li> <a href="http://twiki.softwarelivre.org/bin/view/TWikiBar/TWikiBarPapo002#Macetes_param%C3%A9tricos"> Macetes paramétricos</a></li>
</ul>
</li>
</ul>
</div>
<p>- Garçom! Traz um &#8220;chops&#8221; e dois &#8220;pastel&#8221;. O meu amigo hoje não vai beber por que ele finalmente está sendo apresentado a um verdadeiro sistema operacional e ainda tem muita coisa a aprender!<br />
- E então, amigo, tá entendendo tudo que te expliquei até agora?<br />
- Entendendo eu tô, mas não vi nada prático nisso&#8230;<br />
- Calma rapaz, o que te falei até agora, serve como base ao que há de vir daqui pra frente. Vamos usar estas ferramentas que vimos para montar programas estruturados, que o <i>Shell</i> permite. Você verá porque até na TV já teve programa chamado &#8220;O <i>Shell</i> é o Limite&#8221;.<br />
- Para começar vamos falar dos comandos da família <code>grep</code>.<br />
- <code>grep</code>? Não conheço nenhum termo em inglês com este nome&#8230;<br />
- É claro, <code>grep</code> é um acrônimo <b>Global Regular Expression Print</b>, que usa expressões regulares para pesquisar a ocorrência de cadeias de caracteres na entrada definida (se bem que há uma lenda sobre como este comando foi nomeado: no editor de textos &#8220;ed&#8221;, o avô do &#8220;vim&#8221;, o comando usado para buscas era g/_expressao regular_/p, ou no inglês g/_re_/p.). Por falar em expressões regulares (ou <b>regexp</b>), o <a href="http://www.google.com.br/search?num=100&#38;hl=pt-BR&#38;as_qdr=all&#38;q=%2B%22%5E+EXPRESS%C3%95ES+REGULARES+%24%22+%2Blego+%2B%22como+farejar+um+texto%22&#38;btnG=Pesquisar&#38;meta=" target="_blank">Aurélio Marinho Jargas</a> tem todas as dicas em sua página (inclusive tutorias) que abordam o tema. Se você está mesmo a fim de aprender a programar em <b>Shell</b>, <b>Perl</b>, <b>Python</b>, &#8230; Acho bom você ler estes artigos para te ajudar no que está para vir.</p>
<h2><a title="Eu_fico_com_o_grep_você_com_a_gr" name="Eu_fico_com_o_grep_você_com_a_gr"></a> Eu fico com o <code>grep</code>, você com a gripe</h2>
<p>Esse negócio de gripe é brincadeira! É só um pretexto para pedir umas caipirinhas. Mas voltando à vaca fria, eu te falei que o <code>grep</code> procura cadeia de caracteres dentro de uma entrada definida, mas o que vem a ser uma &#8220;entrada definida&#8221;? Bem, existem várias formas de definir a entrada do comando <code>grep</code>. Vejamos: Pesquisando em um arquivo:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ grep rafael /etc/passwd</div>
<p>Pesquisando em vários arquivos:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ grep grep *.sh</div>
<p>Pesquisando na saida de comando:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ who &#124; grep Pelegrino</div>
<p>No 1º exemplo, o mais simples, procurei a palavra rafael em qualquer lugar do arquivo <code>/etc/passwd</code>. Se quisesse procurá-la como um login name, isto é, somente no início dos registros deste arquivo, eu deveria fazer:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ grep &#8216;^rafael&#8217; /etc/passwd</div>
<p>E para que serve este circunflexo e os apóstrofos, você vai me perguntar. O circunflexo (<code>^</code>), se você tivesse lido os artigos anteriores sobre expressões regulares que te falei, saberia que servem para limitar a pesquisa ao início de cada linha, e os apóstrofos (<code>'</code>) servem para o <i>Shell</i> não interpretar este circunflexo, deixando-o passar incólume para o comando <code>grep</code>.</p>
<p>Olha que legal! O <code>grep</code> aceita como entrada, a saída de outro comando redirecionado por um <code>pipe</code> (isto é muito comum em <i>Shell</i> e é um tremendo acelerador de execução de comando já que atua como se a saída de um programa fosse guardada em disco e o segundo programa lesse este arquivo gerado), desta forma, no 3º exemplo, o comando <code>who</code> listou as pessoas &#8220;logadas&#8221; na mesma máquina que você (não se esqueça jamais: o <i>Linux</i> é multiusuário) e o <code>grep</code> foi usado para verificar se o Pelegrino estava trabalhando ou &#8220;coçando&#8221;.</p>
<h3><a title="A_fam�lia_grep" name="A_fam�lia_grep"></a><a title="A_fam�lia_grep_" name="A_fam�lia_grep_"></a> A família <code>grep</code></h3>
<p>Este comando <code>grep</code> é muito conhecido, pois é usado com muita freqüência, o que muitas pessoas desconhecem é que existem três comandos na família <code>grep</code>, que são:</p>
<ul>
<li> <code>grep</code></li>
<li> <code>egrep</code></li>
<li> <code>fgrep</code></li>
</ul>
<p>A principais características diferenciais entre os 3 são:</p>
<ul>
<li> O <code>grep</code> pode ou não usar expressões regulares simples, porém no caso de não usá-las, o <code>fgrep</code> é melhor, por ser mais rápido;</li>
<li> O <code>egrep</code> (&#8220;e&#8221; de extended, extendido) é muito poderoso no uso de expressões regulares. Por ser o mais lento da família, só deve ser usado quando for necessária a elaboração de uma expressão regular não aceita pelo <code>grep</code>;</li>
<li> O <code>fgrep</code> (&#8220;f&#8221; de fast, rápido, ou de &#8220;file&#8221;, arquivo) como o nome diz é o rapidinho da família, executa o serviço de forma muito veloz (por vezes é cerca de 30% mais veloz que o grep e 50% mais que o egrep), porém não permite o uso de expressões regulares na pesquisa.</li>
</ul>
<div style="border:1px dashed red;min-height:105px;background-color:#ffffcc;margin:1em;padding:1em;"><img src="http://twiki.softwarelivre.org/pub/TWikiBar/FreeSkinImagens/pinguim_atencao.gif" style="float:left;padding:0 8px 0 0;" alt="Pinguim com placa de atenção" /> Tudo que foi dito acima sobre velocidade, só se aplica à família de comandos <code>grep</code> do <i>Unix</i>. No <i>Linux</i> o <code>grep</code> é sempre mais veloz, já que os outros dois (<code>fgrep</code> e <code>egrep</code>) são <i>scripts</i> em <i>Shell</i> que chamam o primeiro e, já vou adiantando, <b>não gosto</b> nem um pouquinho desta solução.</div>
<p>- Agora que você já conhece as diferenças entre os membros da família, me diga: o que você acha dos três exemplos que eu dei antes das explicações?<br />
- Eu achei que o <code>fgrep</code> resolveria o teu problema de forma mais veloz do que o <code>grep</code>.<br />
- Perfeito! Tô vendo que você está atento! Está entendendo tudo que estou te explicando! Então vamos ver mais exemplos para clarear de vez as diferenças de uso dos membros da família.<br />
Exemplos</p>
<p>Eu sei que em um arquivo existe um texto falando sobre <code>Linux</code> só não tenho certeza se está escrito com <code>L</code> maiúsculo ou <code>l</code> minúsculo. Posso fazer de duas formas:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ egrep (Linux &#124; linux) arquivo.txt</div>
<p>ou</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ grep [Ll]inux arquivo.txt</div>
<p>No primeiro caso, a expressão regular complexa <code>"(Linux &#124; linux)"</code> usa os parênteses para agrupar as opções e a barra vertical (<code>&#124;</code>) como um &#8220;ou&#8221; lógico, isto é, estou procurando <code>Linux</code> ou <code>linux</code>.</p>
<p>No segundo, a expressão regular <code>[Ll]inux</code> significa: começado por <code>L</code> ou <code>l</code> seguido de <code>inux</code>. Por esta expressão ser mais simples, o <code>grep</code> consegue resolvê-la, portanto acho melhor usar a segunda forma, já que o <code>egrep</code> tornaria a pesquisa mais lenta.</p>
<p>Outro exemplo. Para listar todos os subdiretórios do diretório corrente, basta:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ ls -l &#124; grep &#8216;^d&#8217;<font color="#ffffff"><br />
drwxr-xr-x   3 root     root         4096 Dec 18  2000 doc<br />
drwxr-xr-x  11 root     root         4096 Jul 13 18:58 freeciv<br />
drwxr-xr-x   3 root     root         4096 Oct 17  2000 gimp<br />
drwxr-xr-x   3 root     root         4096 Aug  8  2000 gnome<br />
drwxr-xr-x   2 root     root         4096 Aug  8  2000 idl<br />
drwxrwxr-x  14 root     root         4096 Jul 13 18:58 locale<br />
drwxrwxr-x  12 root     root         4096 Jan 14  2000 lyx<br />
drwxrwxr-x   3 root     root         4096 Jan 17  2000 pixmaps<br />
drwxr-xr-x   3 root     root         4096 Jul  2 20:30 scribus<br />
drwxrwxr-x   3 root     root         4096 Jan 17  2000 sounds<br />
drwxr-xr-x   3 root     root         4096 Dec 18  2000 xine</font></div>
<p>No exemplo que acabamos de ver, o circunflexo (<code>^</code>) serviu para limitar a pesquisa à primeira posição da saída do <code>ls</code> longo. Os apóstrofos foram colocados para o <i>Shell</i> não &#8220;ver&#8221; o circunflexo (<code>^</code>).</p>
<p>Vamos ver mais um. Sabemos que as quatro primeiras posições possíveis de um <code>ls -l</code> de um arquivo comum (arquivo comum! Não é diretório, nem <i>link</i>, nem &#8230;) devem ser:</p>
<table class="twikiTable" border="0" cellpadding="4" cellspacing="1">
<tr>
<th class="twikiFirstCol" align="center" bgcolor="#0000ff"><b><font color="#ffff00">Posição</font></b></th>
<th bgcolor="#0000ff"><b><font color="#ffff00"> 1ª </font></b></th>
<th bgcolor="#0000ff"><b><font color="#ffff00"> 2ª </font></b></th>
<th bgcolor="#0000ff"><b><font color="#ffff00"> 3ª </font></b></th>
<th align="center" bgcolor="#0000ff"><b><font color="#ffff00"> 4ª </font></b></th>
</tr>
<tr>
<td rowspan="3" class="twikiFirstCol" bgcolor="#dddddd">Valores Possíveis</td>
<td align="center" bgcolor="#dddddd"><code>-</code></td>
<td align="center" bgcolor="#dddddd"><code>r</code></td>
<td align="center" bgcolor="#dddddd"><code>w</code></td>
<td align="center" bgcolor="#dddddd"><code>x</code></td>
</tr>
<tr>
<td bgcolor="#bbbbbb">&#160;</td>
<td align="center" bgcolor="#bbbbbb"><code>-</code></td>
<td align="center" bgcolor="#bbbbbb"><code>-</code></td>
<td align="center" bgcolor="#bbbbbb"><code>s</code> (suid)</td>
</tr>
<tr>
<td bgcolor="#dddddd">&#160;</td>
<td bgcolor="#dddddd">&#160;</td>
<td bgcolor="#dddddd">&#160;</td>
<td align="center" bgcolor="#dddddd"><code>-</code></td>
</tr>
</table>
<p>Assim sendo, para descobrir todos os arquivos executáveis em um determinado diretório eu deveria fazer:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ ls -la &#124; egrep &#8216;^-..(x&#124;s)&#8217;<font color="#ffffff"><br />
-rwxr-xr-x   1 root     root       2875 Jun 18 19:38 rc<br />
-rwxr-xr-x   1 root     root        857 Aug  9 22:03 rc.local<br />
-rwxr-xr-x   1 root     root      18453 Jul  6 17:28 rc.sysinit</font></div>
<p>Onde novamente usamos o circunflexo (<code>^</code>) para limitar a pesquisa ao início de cada linha, então as linhas listadas serão as que começam por um traço (<code>-</code>), seguido de qualquer coisa (o ponto quando usado como uma expressão regular significa qualquer coisa), novamente seguido de qualquer coisa, vindo a seguir um <code>x</code> ou um <code>s</code>.</p>
<p>Obteríamos o mesmo resultado se fizéssemos:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ ls -la &#124; grep &#8216;^-..[xs]&#8216;</div>
<p>e agilizaríamos a pesquisa.</p>
<h2><a title="Vamos_Montar_uma_cdteca" name="Vamos_Montar_uma_cdteca"></a><a title="Vamos_Montar_uma_cdteca_" name="Vamos_Montar_uma_cdteca_"></a> Vamos Montar uma &#8220;cdteca&#8221;</h2>
<p>Vamos começar a desenvolver programas, acho que a montagem de um banco de dados de músicas é bacana para efeito didático (e útil nesses tempos de <i>downloads</i> de mp3 e &#8220;queimadores&#8221; de CDs). Não se esqueça que, da mesma forma que vamos desenvolver um monte de programas para organizar os seus CDs de música, com pequenas adaptações, você pode fazer o mesmo com os CDs de <i>software</i> que vêm com a <b><i>Linux Magazine</i></b> e outros que você compra ou queima, disponibilizando este banco de <i>software</i> para todos que trabalham com você (o <i>Linux</i> é multiusuário, e como tal deve ser explorado), desta forma ganhando muitos pontos com seu adorado chefe.</p>
<p>- Péra ai! De onde eu vou receber os dados dos CDs?<br />
- Inicialmente, vou lhe mostrar como o seu programa pode receber parâmetros de quem o estiver executando e em breve, ensinarei a ler os dados pela tela ou de um arquivo.</p>
<h3><a title="Passando_parâmetros" name="Passando_parâmetros"></a> Passando parâmetros</h3>
<p>O layout do arquivo musicas será o seguinte:</p>
<p><code>nome do álbum^intérprete1~nome da música1:..:intérprete~nome da música</code></p>
<p>isto é, o nome do álbum será separado por um circunflexo (<code>^</code>) do resto do registro, que é formado por diversos grupos compostos pelo intérprete de cada música do CD e a respectiva música interpretada. Estes grupos são separados entre si por dois-pontos (<code>:</code>) e internamente, o intérprete será separado por um til (<code>~</code>) do nome da música.</p>
<p>Eu quero escrever um programa que chamado <code>musinc</code>, que incluirá registros no meu arquivo musicas. Eu passarei o conteúdo de cada álbum como parâmetro na chamada do programa fazendo assim:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ musinc &#8220;álbum^interprete~musica:interprete~musica:&#8230;&#8221;</div>
<p>Desta forma o programa <code>musinc</code> estará recebendo os dados de cada álbum como se fosse uma variável. A única diferença entre um parâmetro recebido e uma variável é que os primeiros recebem nomes numéricos (nome numérico fica muito esquisito, né? O que quis dizer é que seus nomes são formados por um e somente um algarismo), isto é <code>$1, $2, $3, ..., $9</code>. Vamos, antes de tudo, fazer um teste:</p>
<p>Exemplos</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat teste<br />
<font color="#ffffff">#!/bin/bash<br />
# Programa para testar passagem de parametros<br />
echo &#8220;1o. parm -&#62; $1&#8243;<br />
echo &#8220;2o. parm -&#62; $2&#8243;<br />
echo &#8220;3o. parm -&#62; $3&#8243;</font></div>
<p>Vamos executá-lo:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ teste passando parametros para testar<br />
<font color="#ffffff">bash: teste: cannot execute</font></div>
<p>Ops! Esqueci-me de torná-lo executável. Vou fazê-lo de forma a permitir que todos possam executá-lo e em seguida vou testá-lo:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ chmod 755 teste<br />
$ teste passando parametros para testar<br />
<font color="#ffffff">1o. parm -&#62; passando<br />
2o. parm -&#62; parametros<br />
3o. parm -&#62; para</font></div>
<p>Repare que a palavra <code>testar</code>, que seria o quarto parâmetro, não foi listada. Isto deu-se justamente porque o programa teste só listava os três primeiros parâmetros. Vamos executá-lo de outra forma:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ teste &#8220;passando parametros&#8221; para testar<font color="#ffffff"><br />
1o. parm -&#62; passando parametros<br />
2o. parm -&#62; para<br />
3o. parm -&#62; testar</font></div>
<p>As aspas não deixaram o <code>Shell</code> ver o espaço em branco entre as palavras e considerou-as um único parâmetro.</p>
<h3><a title="Macetes_paramétricos" name="Macetes_paramétricos"></a> Macetes paramétricos</h3>
<p>Já que estamos falando em passagem de parâmetros deixa eu te dar mais umas dicas:</p>
<table class="twikiTable" border="0" cellpadding="4" cellspacing="1">
<tr>
<th colspan="2" class="twikiFirstCol" align="center" bgcolor="#0000ff"><b><font color="#ffff00">Significado das Principais Variáveis Referentes aos Parâmetros</font></b></th>
</tr>
<tr>
<td class="twikiFirstCol" bgcolor="#dddddd"><b>Variável</b></td>
<td bgcolor="#dddddd"><b>Significado</b></td>
</tr>
<tr>
<td class="twikiFirstCol" align="center" bgcolor="#bbbbbb"><code>$0</code></td>
<td bgcolor="#bbbbbb">Contém o nome do programa</td>
</tr>
<tr>
<td class="twikiFirstCol" align="center" bgcolor="#dddddd"><code>$#</code></td>
<td bgcolor="#dddddd">Contém a quantidade de parâmetros passados</td>
</tr>
<tr>
<td class="twikiFirstCol" align="center" bgcolor="#bbbbbb"><code>$*</code></td>
<td bgcolor="#bbbbbb">Contém o conjunto de todos os parâmetros (muito parecido com <code>$@</code>)</td>
</tr>
</table>
<p>Exemplos</p>
<p>Vamos alterar o programa <code>teste</code> para usar as variáveis que acabamos de ver. Vamos fazê-lo assim:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat teste<br />
<font color="#ffffff">#!/bin/bash<br />
# Programa para testar passagem de parametros (2a. Versao)<br />
echo O programa $0 recebeu $# parametros<br />
echo &#8220;1o. parm -&#62; $1&#8243;<br />
echo &#8220;2o. parm -&#62; $2&#8243;<br />
echo &#8220;3o. parm -&#62; $3&#8243;<br />
echo Todos de uma só &#8220;tacada&#8221;: $*</font></div>
<p>Repare que antes das aspas eu usei uma barra invertida para o escondê-las da interpretação do <i>Shell</i> (se não usasse as contrabarras as aspas não apareceriam). Vamos executá-lo:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ teste passando parametros para testar<br />
<font color="#ffffff">O programa teste recebeu 4 parametros<br />
1o. parm -&#62; passando<br />
2o. parm -&#62; parametros<br />
3o. parm -&#62; para<br />
Todos de uma só &#8220;tacada&#8221;: passando parametros para testar</font></div>
<p>Conforme eu disse, os parâmetros recebem números de <code>1</code> a  <code>9</code>, mas isso não significa que não posso usar mais de 9 parâmetros significa somente que só posso endereçar 9. Vamos testar isso:</p>
<p>Exemplo:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat teste<br />
<font color="#ffffff">#!/bin/bash<br />
# Programa para testar passagem de parametros (3a. Versao)<br />
echo O programa $0 recebeu $# parametros<br />
echo &#8220;11o. parm -&#62; $11&#8243;<br />
shift<br />
echo &#8220;2o. parm -&#62; $1&#8243;<br />
shift 2<br />
echo &#8220;4o. Parm -&#62; $1&#8243;</font></div>
<p>Vamos executá-lo:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ teste passando parametros para testar<br />
<font color="#ffffff">O programa teste recebeu 4 parametros que são:<br />
11o. parm -&#62; passando1<br />
2o. parm -&#62; parametros<br />
4o. parm -&#62; testar</font></div>
<p>Duas coisas muito interessantes neste <i>script</i>:</p>
<ol>
<li> Para mostrar que os nomes dos parâmetros variam de <code>$1</code> a <code>$9</code> eu fiz um echo <code>$11</code> e o que aconteceu? O <i>Shell</i> interpretou como sendo <code>$1</code> seguido do algarismo <code>1</code> e listou <code>passando1</code>;</li>
<li> O comando <code>shift</code> cuja sintaxe é <code>shift n</code>, podendo o <code>n</code> assumir qualquer valor numérico (porém seu <i>default</i> é <code>1</code> como no exemplo dado), despreza os <code>n</code> primeiros parâmetros, tornando o parâmetro de ordem <code>n+1</code>, o primeiro ou seja, o <code>$1</code>.</li>
</ol>
<p>Bem, agora que você já sabe mais sobre passagem de parâmetros do que eu, vamos voltar à nossa &#8220;cdteca&#8221; para fazer o <i>script</i> de inclusão de CDs no meu banco chamado <code>musicas</code>. O programa é muito simples (como tudo em <i>Shell</i>) e vou listá-lo para você ver:</p>
<p>Exemplos</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat musinc<br />
<font color="#ffffff">#!/bin/bash<br />
# Cadastra CDs (versao 1)<br />
#<br />
echo $1 &#62;&#62; musicas</font></div>
<p>O <i>script</i> é fácil e funcional, limito-me a anexar ao fim do arquivo <code>musicas</code> o parâmetro recebido. Vamos cadastrar 3 álbuns para ver se funciona (para não ficar &#8220;enchendo lingüiça&#8221;, vou supor que em cada CD só existem 2 músicas):</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ musinc &#8220;album 3^Artista5~Musica5:Artista6~Musica5&#8243;<br />
$ musinc &#8220;album 1^Artista1~Musica1:Artista2~Musica2&#8243;<br />
$ musinc &#8220;album 2^Artista3~Musica3:Artista4~Musica4&#8243;</div>
<p>Listando o conteúdo de musicas.</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat musicas<br />
<font color="#ffffff">album 3^Artista5~Musica5:Artista6~Musica6<br />
album 1^Artista1~Musica1:Artista2~Musica2<br />
album 2^Artista3~Musica3:Artista4~Musica4</font></div>
<p>Não está funcional como achava que deveria ficar&#8230; podia ter ficado melhor. Os álbuns estão fora de ordem, dificultando a pesquisa. Vamos alterar nosso <i>script</i> e depois testá-lo novamente:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat musinc<br />
<font color="#ffffff">#!/bin/bash<br />
# Cadastra CDs (versao 2)<br />
#<br />
echo $1 &#62;&#62; musicas<br />
sort musicas -o musicas</font></div>
<p>Vamos cadastrar mais um:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ musinc &#8220;album 4^Artista7~Musica7:Artista8~Musica8&#8243;</div>
<p>Agora vamos ver o que aconteceu com o arquivo <code>musicas</code>:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat musicas<br />
<font color="#ffffff">album 1^Artista1~Musica1:Artista2~Musica2<br />
album 2^Artista3~Musica3:Artista4~Musica4<br />
album 3^Artista5~Musica5:Artista6~Musica5<br />
album 4^Artista7~Musica7:Artista8~Musica8</font></div>
<p>Simplesmente inseri uma linha que classifica o arquivo <code>musicas</code> dando a saída nele mesmo (para isso serve a opção <code>-o</code>), após cada álbum ser anexado.</p>
<p>Oba! Agora está legal e quase funcional. Mas atenção, não se desespere! Esta não é a versão final. O programa ficará muito melhor e mais amigável, em uma nova versão que desenvolveremos após aprendermos a adquirir os dados da tela e formatar a entrada.</p>
<p>Exemplos</p>
<p>Ficar listando com o comando <code>cat</code> não está com nada, vamos então fazer um programa chamado <code>muslist</code> para listar um álbum cujo nome será passado como parâmetro:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat muslist<br />
<font color="#ffffff">#!/bin/bash<br />
# Consulta CDs (versao 1)<br />
#<br />
grep $1 musicas</font></div>
<p>Vamos executá-lo, procurando pelo <code>album 2</code>. Como já vimos antes, para passar a cadeia <code>album 2</code> é necessário protegê-la da interpretação do <i>Shell</i>, para que ele não a interprete como dois parâmetros. Vamos fazer assim:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ muslist &#8220;álbum 2&#8243;<br />
<font color="#ffffff">grep: can&#8217;t open 2<br />
musicas: album 1^Artista1~Musica1:Artista2~Musica2<br />
musicas: album 2^Artista3~Musica3:Artista4~Musica4<br />
musicas: album 3^Artista5~Musica5:Artista6~Musica6<br />
musicas: album 4^Artista7~Musica7:Artista8~Musica8</font></div>
<p>Que lambança! Onde está o erro? Eu tive o cuidado de colocar o parâmetro passado entre aspas, para o <i>Shell</i> não dividi-lo em dois!</p>
<p>É, mas repare como está o <code>grep</code> executado:</p>
<p><code>grep $1 musicas</code></p>
<p>Mesmo colocando <code>álbum 2</code> entre aspas, para que fosse encarado como um único parâmetro, quando o <code>$1</code> foi passado pelo <i>Shell</i> para o comando <code>grep</code>, transformou-se em dois argumentos. Desta forma o conteúdo final da linha, que o comando <code>grep</code> executou foi o seguinte:</p>
<p><code>grep album 2 musicas</code></p>
<p>Como a sintaxe do <code>grep</code> é:</p>
<p>=grep  [arq1, arq2, ..., arqn]=</p>
<p>o <code>grep</code> entendeu que deveria procurar a cadeia de caracteres <code>album</code> nos <code>arquivos 2</code> e <code>musicas</code>, Por não existir o <code>arquivo 2</code> gerou o erro, e por encontrar a palavra <code>album</code> em todos os registros de <code>musicas</code>, listou a todos.</p>
<div style="border:1px dashed red;min-height:121px;background-color:#ffffcc;margin:1em;padding:1em;"><img src="http://twiki.softwarelivre.org/pub/TWikiBar/FreeSkinImagens/pinguim_dica.gif" style="float:left;padding:0 8px 0 0;" alt="Pinguim com placa de dica" align="left" /> Sempre que a <code>cadeia de caracteres</code> a ser passada para o comando <code>grep</code> possuir brancos ou <code>TAB</code>, mesmo que dentro de variáveis, coloque-a sempre entre aspas para evitar que as palavras após o primeiro espaço em branco ou <code>TAB</code> sejam interpretadas como nomes de arquivos.</div>
<p>Por outro lado, é melhor ignorarmos maiúsculas e minúsculas na pesquisa. Resolveríamos os dois problemas se o programa tivesse a seguinte forma:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat muslist<br />
<font color="#ffffff">#!/bin/bash<br />
# Consulta CDs (versao 2)<br />
#<br />
grep -i &#8220;$1&#8243; musicas</font></div>
<p>Neste caso, usamos a opção <code>-i</code> do <code>grep</code>, que como já vimos, serve para ignorar maiúsculas e minúsculas, e colocamos o <code>$1</code> entre aspas, para que o <code>grep</code> continuasse a ver a cadeia de caracteres resultante da expansão da linha pelo <code>Shell</code> como um único argumento de pesquisa.</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ muslist &#8220;album 2&#8243;<font color="#ffffff"><br />
album2^Artista3~Musica3:Artista4~Musica4</font></div>
<p>Agora repare que o <code>grep</code> localiza a cadeia pesquisada em qualquer lugar do registro, então da forma que estamos fazendo, podemos pesquisar por álbum, por música, por intérprete ou até por um pedaço de qualquer um destes. Quando conhecermos os comandos condicionais, montaremos uma nova versão de <code>muslist</code> que permitirá especificar por qual campo pesquisar.</p>
<p>Aí você vai me dizer:</p>
<p>- Poxa, mas é um saco ter que colocar o argumento de pesquisa entre aspas na hora de passar o nome do álbum. Esta forma não é nem um pouco amigável!<br />
- Tem razão, e por isso vou te mostrar uma outra forma de fazer o que você pediu:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat muslist<br />
<font color="#ffffff">#!/bin/bash<br />
# Consulta CDs (versao 3)<br />
#<br />
grep -i &#8220;$*&#8221; musicas<br />
$ muslist album 2<br />
album 2^Artista3~Musica3:Artista4~Musica4</font></div>
<p>Desta forma, o <code>$*</code>, que significa todos os parâmetros, será substituído pela cadeia <code>album 2</code> (de acordo com o exemplo anterior, fazendo o que você queria.</p>
<p>Não se esqueça o problema do <i>Shell</i> não é se você pode ou não fazer uma determinada coisa. O problema é decidir qual é a melhor forma de fazê-la, já que para desempenhar qualquer tarefa, a quantidade de opções é enorme.</p>
<p>Ah! Em um dia de verão você foi à praia, esqueceu o CD no carro, aquele &#8220;solzinho&#8221; de 40 graus empenou o seu CD e agora você precisa de uma ferramenta para removê-lo do banco de dados? Não tem problema, vamos desenvolver um <i>script</i> chamado <code>musexc</code>, para excluir estes CDs.</p>
<p>Antes de desenvolver o &#8220;bacalho&#8221;, quero te apresentar a uma opção bastante útil da família de comandos <code>grep</code>. É a opção <code>-v</code>, que quando usada lista todos os registros da entrada, exceto o(s) localizado(s) pelo comando. Vejamos:</p>
<p>Exemplos</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ grep -v &#8220;album 2&#8243; musicas<br />
<font color="#ffffff">album 1^Artista1~Musica1:Artista2~Musica2<br />
album 3^Artista5~Musica5:Artista6~Musica6<br />
album 4^Artista7~Musica7:Artista8~Musica8</font></div>
<p>Conforme eu expliquei antes, o <code>grep</code> do exemplo listou todos os registros de musicas exceto o referente a <code>album 2</code>, porque atendia ao argumento do comando. Estamos então prontos para desenvolver o <i>script</i> para remover aquele CD empenado da sua &#8220;CDteca&#8221;. Ele tem a seguinte cara:</p>
<div style="border:1px none;background:#000000 none no-repeat scroll right top;overflow:auto;font-family:Courier,'Courier New','Lucida Console','Bitstream Vera Sans Mono',Monaco,monospace;white-space:pre;font-size:100%;line-height:1em;color:yellow;margin:1em 0.5em;padding:1.5em 1em;">$ cat musexc<br />
<font color="#ffffff">#!/bin/bash<br />
# Exclui CDs (versao 1)<br />
#<br />
grep -v &#8220;$1&#8243; musicas &#62; /tmp/mus$$<br />
mv -f /tmp/mus$$ musicas</font></div>
<p>Na primeira linha mandei para <code>/tmp/mus$$</code> o arquivo musicas, sem os registros que atendessem a consulta feita pelo comando <code>grep</code>. Em seguida, movi (que, no duro, equivale a renomear) <code>/tmp/mus$$</code> por cima do antigo <code>musicas</code>.</p>
<p>Usei o arquivo <code>/tmp/mus$$</code> como arquivo de trabalho, porque como já havia citado no artigo anterior, o <code>$$</code> contém o <code>PID</code> (<i>Process Identification</i> ou identificação do processo) e desta forma cada um que editar o arquivo <code>musicas</code> o fará em um arquivo de trabalho diferente, desta forma evitando colisões no uso.</p>
<p>- Aê cara, estes programas que fizemos até aqui estão muito primários em virtude da falta de ferramentas que ainda temos. Mas é bom, enquanto eu tomo mais um chope, você ir para casa praticar em cima dos exemplos dados porque, eu prometo, chegaremos a desenvolver um sistema bacana para controle dos seus CDs.<br />
- Quando nos encontrarmos da próxima vez, vou te ensinar como funcionam os comandos condicionais e aprimoraremos mais um pouco estes <i>scripts</i>.<br />
- Por hoje chega! Já falei demais e preciso molhar a palavra porque estou de goela seca!<br />
- Garçom! Mais um sem colarinho!</p>
<p>Vou aproveitar também para mandar o meu jabá: diga para os amigos que quem estiver afim de fazer um curso porreta de programação em <i>Shell</i> que mande um e-mail para a nossa <a href="mailto:treinamentos@festivalsoftwarelivre.org?Subject=Curso%20de%20Shell%20com%20Julio%20Neves">gerencia de treinamento</a> para informar-se.</p>
<p>Qualquer dúvida ou falta de companhia para um chope ou até para falar mal dos políticos é só mandar um e-mail para <a href="mailto:julioneves@openoffice.org?Subject=D%C3%BAvidas%20Papo%20de%20Botequim">mim</a>.</p>
<p>Valeu!</p>
</div>]]></content:encoded>
</item>
<item>
<title><![CDATA[Regular Expressions Video Series]]></title>
<link>http://dbalink.wordpress.com/2008/01/23/34/</link>
<pubDate>Wed, 23 Jan 2008 07:51:05 +0000</pubDate>
<dc:creator>MarlonRibunal</dc:creator>
<guid>http://dbalink.wordpress.com/2008/01/23/34/</guid>
<description><![CDATA[Ok Heroes. Regular Expressions Series In this webcast series, we explore an unsung hero: the regular]]></description>
<content:encoded><![CDATA[Ok Heroes. Regular Expressions Series In this webcast series, we explore an unsung hero: the regular]]></content:encoded>
</item>
<item>
<title><![CDATA[Python and Grep Regular Expressions Tutorial]]></title>
<link>http://bookmarks.honewatson.com/2007/10/31/python-and-grep-regular-expressions-tutorial/</link>
<pubDate>Wed, 31 Oct 2007 02:46:34 +0000</pubDate>
<dc:creator>honewatson</dc:creator>
<guid>http://bookmarks.honewatson.com/2007/10/31/python-and-grep-regular-expressions-tutorial/</guid>
<description><![CDATA[Regular expression tutorials for Python and Grep. Tutorial One Tutorial Two]]></description>
<content:encoded><![CDATA[<div class='snap_preview'><p>Regular expression tutorials for Python and Grep.</p>
<p><a href="http://gnosis.cx/publish/programming/regular_expressions.html">Tutorial One</a></p>
<p><a href="http://etext.lib.virginia.edu/services/helpsheets/unix/regex.html">Tutorial Two</a></p>
</div>]]></content:encoded>
</item>

</channel>
</rss>
