perl
Differences
This shows you the differences between two versions of the page.
| Next revision | Previous revision | ||
| perl [2018/12/06 21:05] – created 91.177.234.129 | perl [2025/02/27 16:09] (current) – external edit 127.0.0.1 | ||
|---|---|---|---|
| Line 1: | Line 1: | ||
| - | ====== | + | * [[https:// |
| - | + | * [[http:// | |
| - | * [[http:// | + | * [[http:// |
| - | * [[http:// | + | |
| Some one liners: [[http:// | Some one liners: [[http:// | ||
| - | ======Oneliners====== | + | ===== Install local version of Perl without needing root access ==== |
| + | If installing locally with a lighttpd webserver, see here for a lighttpd.conf file [[html css javascript]] | ||
| + | < | ||
| + | wget https:// | ||
| + | tar -xzf perl-5.34.0.tar.gz | ||
| + | cd perl-5.34.0 | ||
| + | mkdir -p $HOME/ | ||
| + | ./Configure -des -Dprefix=$HOME/ | ||
| + | make | ||
| + | make test | ||
| + | make install | ||
| + | export PATH=" | ||
| + | </ | ||
| + | |||
| + | ==== Install additional modules locally without root access ==== | ||
| + | Install this first one (Local:: | ||
| + | * Search CPAN for the module and click the download link on the left hand side | ||
| + | * Copy the .gz file to a source directory and unzip it | ||
| + | < | ||
| + | mkdir ~/ | ||
| + | mv local-lib-2.000028.tar.gz ~/ | ||
| + | cd ~/ | ||
| + | tar -zxvf local-lib-2.000028.tar.gz | ||
| + | cd local-lib-2.000028 | ||
| + | </ | ||
| + | * Use a prefix to force local installation | ||
| + | < | ||
| + | perl Makefile.PL PREFIX=~/ | ||
| + | make && make test && make install | ||
| + | </ | ||
| + | * Now additional modules can be installed using Local:: | ||
| + | < | ||
| + | perl -MCPAN -Mlocal:: | ||
| + | </ | ||
| + | |||
| + | |||
| + | ===== Oneliners ===== | ||
| + | Remove all non-ascii characters from a text file\\ | ||
| + | If 'cat -v' shows up weird characters in the file, they can be removed like this: | ||
| + | < | ||
| + | perl -pe ' | ||
| + | </ | ||
| + | |||
| + | Print out just the connect identifiers of the connection clauses in tnsnames.ora\\ | ||
| + | match an alphabetic or numeric (not space) as first character followed by any number of characters until the first = | ||
| + | < | ||
| + | perl -n -e 'print " | ||
| + | </ | ||
| + | |||
| + | To spit out only the stanzas in tnsnames.ora where the host and port are specific values | ||
| + | < | ||
| + | </ | ||
| + | Change the connect identifier in tnsnames.ora to upper case (anything from the start of line up to "= (" ) | ||
| + | < | ||
| + | perl -p -i -e ' | ||
| + | </ | ||
| + | |||
| + | To spit out only the stanzas in / | ||
| + | < | ||
| + | perl -ne 'BEGIN { $/ | ||
| + | </ | ||
| + | To modify the value in a variable | ||
| + | < | ||
| + | $variable =~ s/ | ||
| + | eg: | ||
| + | $sid =~ s/ | ||
| + | </ | ||
| To change only the fifth line, you can add a test checking $., the input line number, then only perform the operation when the test passes: | To change only the fifth line, you can add a test checking $., the input line number, then only perform the operation when the test passes: | ||
| - | < | + | < |
| + | perl -pi -e ' | ||
| + | </ | ||
| To add lines before a certain line, you can add a line (or lines!) before Perl prints $_: | To add lines before a certain line, you can add a line (or lines!) before Perl prints $_: | ||
| - | < | + | < |
| + | perl -pi -e 'print "Put before third line\n" | ||
| + | </ | ||
| You can even add a line to the beginning of a file, since the current line prints at the end of the loop: | You can even add a line to the beginning of a file, since the current line prints at the end of the loop: | ||
| - | < | + | < |
| + | perl -pi -e 'print "Put before first line\n" | ||
| + | </ | ||
| To insert a line after one already in the file, use the -n switch. It's just like -p except that it doesn' | To insert a line after one already in the file, use the -n switch. It's just like -p except that it doesn' | ||
| - | < | + | < |
| + | perl -ni -e ' | ||
| + | </ | ||
| To delete lines, only print the ones that you want. | To delete lines, only print the ones that you want. | ||
| - | < | + | < |
| + | perl -ni -e 'print unless /d/' inFile.txt | ||
| + | </ | ||
| … or … | … or … | ||
| - | < | + | < |
| + | perl -pi -e 'next unless /d/' inFile.txt | ||
| + | </ | ||
| + | ==== Another set of useful one-liner tricks ==== | ||
| + | * Trick #1: -l (lower case L) | ||
| + | Smart newline processing. Normally, perl hands you entire lines, including a trailing newline. With -l, it will strip the trailing newline off of any lines read, and automatically add a newline to anything you print (including via -p). | ||
| + | Suppose I wanted to strip trailing whitespace from a file. I might naïvely try something like | ||
| - | =====Using %ENV to pass parameters to a perl one-liner===== | + | < |
| - | Used here to clean up a comma-separated list of parameters passed into a shell.< | + | perl -pe 's/\s*$//' |
| - | < | + | </ |
| - | =====Add a line after another one in a file using Perl===== | + | The problem, however, is that the line ends with " |
| - | Use Perl to filter a script (or a load of scripts) and add an extra line when certain pattern match condition exists.<br /> | + | |
| + | |||
| + | |||
| + | < | ||
| + | perl -lpe ' | ||
| + | </ | ||
| + | |||
| + | |||
| + | * Trick #2: -0 | ||
| + | Occasionally, | ||
| + | |||
| + | < | ||
| + | find . -name ' | ||
| + | </ | ||
| + | Could be used to delete all ~-files in a directory tree, without having to remember how xargs works. | ||
| + | |||
| + | * Trick #3: -i (lower case I) | ||
| + | -i tells perl to operate on files in-place. If you use -n or -p with -i, and you pass perl filenames on the command-line, | ||
| + | |||
| + | < | ||
| + | perl -i.bak -ne 'print unless /^#/' script.sh | ||
| + | </ | ||
| + | Would strip all whole-line commands from script.sh, but leave a copy of the original in script.sh.bak. | ||
| + | |||
| + | * Trick #4: The .. operator | ||
| + | Perl's .. operator is a stateful operator -- it remembers state between evaluations. As long as its left operand is false, it returns false; Once the left hand returns true, it starts evaluating the right-hand operand until that becomes true, at which point, on the next iteration it resets to false and starts testing the other operand again. | ||
| + | |||
| + | What does that mean in practice? It's a range operator: It can be easily used to act on a range of lines in a file. For instance, I can extract all GPG public keys from a file using: | ||
| + | |||
| + | < | ||
| + | perl -ne 'print if /-----BEGIN PGP PUBLIC KEY BLOCK-----/ | ||
| + | </ | ||
| + | * Trick #5: -a | ||
| + | -a turns on autosplit mode – perl will automatically split input lines on whitespace into the @F array. If you ever run into any advice that accidentally escaped from 1980 telling you to use awk because it automatically splits lines into fields, this is how you use perl to do the same thing without learning another, even worse, language. | ||
| + | |||
| + | As an example, you could print a list of files along with their link counts using | ||
| + | |||
| + | < | ||
| + | ls -l | perl -lane 'print "$F[7] $F[1]"' | ||
| + | </ | ||
| + | |||
| + | |||
| + | * Trick #6: -F | ||
| + | -F is used in conjunction with -a, to choose the delimiter on which to split lines. To print every user in /etc/passwd (which is colon-separated with the user in the first column), we could do: | ||
| + | |||
| + | < | ||
| + | perl -F: -lane 'print $F[0]' / | ||
| + | </ | ||
| + | |||
| + | * Trick #7: \K | ||
| + | \K is undoubtedly my favorite little-known-feature of Perl regular expressions. | ||
| + | This is most useful in conjunction with < | ||
| + | |||
| + | Suppose I want to replace the From: field in an email. We could write something like | ||
| + | |||
| + | < | ||
| + | perl -lape ' | ||
| + | </ | ||
| + | But having to parenthesize the right bit and include the $1 is annoying and error-prone. We can simplify the regex by using \K to tell perl we won't want to replace the start of the match: | ||
| + | |||
| + | < | ||
| + | perl -lape ' | ||
| + | </ | ||
| + | * Trick #8: $ENV{} | ||
| + | When you're writing a one-liner using -e in the shell, you generally want to quote it with ', so that dollar signs inside the one-liner aren't expanded by the shell. But that makes it annoying to use a ' inside your one-liner, since you can't escape a single quote inside of single quotes, in the shell. | ||
| + | |||
| + | Let's suppose we wanted to print the username of anyone in /etc/passwd whose name included an apostrophe. One option would be to use a standard shell-quoting trick to include the ': | ||
| + | |||
| + | < | ||
| + | perl -F: -lane 'print $F[0] if $F[4] =~ /'"'"'/' | ||
| + | </ | ||
| + | But counting apostrophes and backslashes gets old fast. A better option, in my opinion, is to use the environment to pass the regex into perl, which lets you dodge a layer of parsing entirely: | ||
| + | |||
| + | < | ||
| + | env re="'" | ||
| + | </ | ||
| + | We use the env command to place the regex in a variable called re, which we can then refer to from the perl script through the %ENV hash. This way is slightly longer, but I find the savings in counting backslashes or quotes to be worth it, especially if you need to end up embedding strings with more than a single metacharacter. | ||
| + | |||
| + | * Trick #9: BEGIN and END | ||
| + | BEGIN { ... } and END { ... } let you put code that gets run entirely before or after the loop over the lines. | ||
| + | |||
| + | For example, I could sum the values in the second column of a CSV file using: | ||
| + | |||
| + | < | ||
| + | perl -F, -lane '$t += $F[1]; END { print $t }' | ||
| + | </ | ||
| + | * Trick #10: -MRegexp:: | ||
| + | Using -M on the command line tells perl to load the given module before running your code. There are thousands of modules available on CPAN, numerous of them potentially useful in one-liners, but one of my favorite for one-liner use is Regexp:: | ||
| + | |||
| + | The full set of regexes available in Regexp:: | ||
| + | |||
| + | Neither the ifconfig nor the ip tool that is supposed to replace it provide, as far as I know, an easy way of extracting information for use by scripts. The ifdata program provides such an interface, but isn't installed everywhere. Using perl and Regexp:: | ||
| + | |||
| + | < | ||
| + | ip address list eth0 | \nperl -MRegexp:: | ||
| + | </ | ||
| + | |||
| + | ==== Perl oneliners from catonmat.net ==== | ||
| + | Reference: [[https:// | ||
| + | < | ||
| + | Useful One-Line Scripts for Perl Jan 27 2019 | version 1.12 | ||
| + | -------------------------------- | ||
| + | |||
| + | Compiled by Peter Krumins ([email protected], | ||
| + | https:// | ||
| + | |||
| + | Latest version of this file is always at: | ||
| + | |||
| + | https:// | ||
| + | |||
| + | This file is also available in other languages: | ||
| + | |||
| + | Chinese: https:// | ||
| + | |||
| + | Please email me [email protected] if you want to translate it. | ||
| + | |||
| + | Perl One-Liners on Github: | ||
| + | |||
| + | https:// | ||
| + | |||
| + | You can send me pull requests over GitHub! I accept bug fixes, | ||
| + | new one-liners, translations and everything else related. | ||
| + | |||
| + | I have also written "Perl One-Liners Explained" | ||
| + | this file. It explains all the one-liners here. Get it at: | ||
| + | |||
| + | https:// | ||
| + | |||
| + | No Starch Press has published "Perl One-Liners" | ||
| + | |||
| + | https:// | ||
| + | |||
| + | These one-liners work both on UNIX systems and Windows. Most likely your | ||
| + | UNIX system already has Perl. For Windows get the Strawberry Perl at: | ||
| + | |||
| + | http:// | ||
| + | |||
| + | Table of contents: | ||
| + | |||
| + | 1. File Spacing | ||
| + | 2. Line Numbering | ||
| + | 3. Calculations | ||
| + | 4. String Creation and Array Creation | ||
| + | 5. Text Conversion and Substitution | ||
| + | 6. Selective Printing and Deleting of Certain Lines | ||
| + | 7. Handy Regular Expressions | ||
| + | 8. Perl tricks | ||
| + | |||
| + | |||
| + | FILE SPACING | ||
| + | ------------ | ||
| + | |||
| + | # Double space a file | ||
| + | perl -pe ' | ||
| + | perl -pe 'BEGIN { $\=" | ||
| + | perl -pe '$_ .= " | ||
| + | perl -pe ' | ||
| + | perl -nE ' | ||
| + | |||
| + | # Double space a file, except the blank lines | ||
| + | perl -pe '$_ .= " | ||
| + | perl -pe '$_ .= " | ||
| + | |||
| + | # Triple space a file | ||
| + | perl -pe ' | ||
| + | perl -pe ' | ||
| + | |||
| + | # N-space a file | ||
| + | perl -pe ' | ||
| + | |||
| + | # Add a blank line before every line | ||
| + | perl -pe ' | ||
| + | |||
| + | # Remove all blank lines | ||
| + | perl -ne 'print unless / | ||
| + | perl -lne 'print if length' | ||
| + | perl -ne 'print if / | ||
| + | |||
| + | # Remove all consecutive blank lines, leaving just one | ||
| + | perl -00 -pe '' | ||
| + | perl -00pe0 | ||
| + | |||
| + | # Compress/ | ||
| + | perl -00 -pe ' | ||
| + | |||
| + | # Fold a file so that every set of 10 lines becomes one tab-separated line | ||
| + | perl -lpe '$\ = $. % 10 ? " | ||
| + | |||
| + | |||
| + | LINE NUMBERING | ||
| + | -------------- | ||
| + | |||
| + | # Number all lines in a file | ||
| + | perl -pe '$_ = "$. $_"' | ||
| + | |||
| + | # Number only non-empty lines in a file | ||
| + | perl -pe '$_ = ++$a." $_" if /./' | ||
| + | |||
| + | # Number and print only non-empty lines in a file (drop empty lines) | ||
| + | perl -ne 'print ++$a." $_" if /./' | ||
| + | |||
| + | # Number all lines but print line numbers only non-empty lines | ||
| + | perl -pe '$_ = "$. $_" if /./' | ||
| + | |||
| + | # Number only lines that match a pattern, print others unmodified | ||
| + | perl -pe '$_ = ++$a." $_" if / | ||
| + | |||
| + | # Number and print only lines that match a pattern | ||
| + | perl -ne 'print ++$a." $_" if / | ||
| + | |||
| + | # Number all lines, but print line numbers only for lines that match a pattern | ||
| + | perl -pe '$_ = "$. $_" if / | ||
| + | |||
| + | # Number all lines in a file using a custom format (emulate cat -n) | ||
| + | perl -ne ' | ||
| + | |||
| + | # Print the total number of lines in a file (emulate wc -l) | ||
| + | perl -lne 'END { print $. }' | ||
| + | perl -le 'print $n=()=<>' | ||
| + | perl -le 'print scalar(()=<> | ||
| + | perl -le 'print scalar(@foo=<> | ||
| + | perl -ne ' | ||
| + | perl -nE '}{say $.' | ||
| + | |||
| + | # Print the number of non-empty lines in a file | ||
| + | perl -le 'print scalar(grep{/ | ||
| + | perl -le 'print ~~grep{/ | ||
| + | perl -le ' | ||
| + | perl -E ' | ||
| + | |||
| + | # Print the number of empty lines in a file | ||
| + | perl -lne '$a++ if /^$/; END {print $a+0}' | ||
| + | perl -le 'print scalar(grep{/ | ||
| + | perl -le 'print ~~grep{/ | ||
| + | perl -E ' | ||
| + | |||
| + | # Print the number of lines in a file that match a pattern (emulate grep -c) | ||
| + | perl -lne '$a++ if /regex/; END {print $a+0}' | ||
| + | perl -nE '$a++ if /regex/; END {say $a+0}' | ||
| + | |||
| + | |||
| + | CALCULATIONS | ||
| + | ------------ | ||
| + | |||
| + | # Check if a number is a prime | ||
| + | perl -lne ' | ||
| + | |||
| + | # Print the sum of all the fields on a line | ||
| + | perl -MList:: | ||
| + | |||
| + | # Print the sum of all the fields on all lines | ||
| + | perl -MList:: | ||
| + | perl -MList:: | ||
| + | |||
| + | # Shuffle all fields on a line | ||
| + | perl -MList:: | ||
| + | perl -MList:: | ||
| + | |||
| + | # Find the minimum element on a line | ||
| + | perl -MList:: | ||
| + | |||
| + | # Find the minimum element over all the lines | ||
| + | perl -MList:: | ||
| + | perl -MList:: | ||
| + | |||
| + | # Find the maximum element on a line | ||
| + | perl -MList:: | ||
| + | |||
| + | # Find the maximum element over all the lines | ||
| + | perl -MList:: | ||
| + | |||
| + | # Replace each field with its absolute value | ||
| + | perl -alne 'print " | ||
| + | |||
| + | # Find the total number of fields (words) on each line | ||
| + | perl -alne 'print scalar @F' | ||
| + | |||
| + | # Print the total number of fields (words) on each line followed by the line | ||
| + | perl -alne 'print scalar @F, " $_"' | ||
| + | |||
| + | # Find the total number of fields (words) on all lines | ||
| + | perl -alne '$t += @F; END { print $t}' | ||
| + | |||
| + | # Print the total number of fields that match a pattern | ||
| + | perl -alne 'map { /regex/ && $t++ } @F; END { print $t }' | ||
| + | perl -alne '$t += /regex/ for @F; END { print $t }' | ||
| + | perl -alne '$t += grep /regex/, @F; END { print $t }' | ||
| + | |||
| + | # Print the total number of lines that match a pattern | ||
| + | perl -lne '/ | ||
| + | |||
| + | # Print the number PI to n decimal places | ||
| + | perl -Mbignum=bpi -le 'print bpi(n)' | ||
| + | |||
| + | # Print the number PI to 39 decimal places | ||
| + | perl -Mbignum=PI -le 'print PI' | ||
| + | |||
| + | # Print the number E to n decimal places | ||
| + | perl -Mbignum=bexp -le 'print bexp(1, | ||
| + | |||
| + | # Print the number E to 39 decimal places | ||
| + | perl -Mbignum=e -le 'print e' | ||
| + | |||
| + | # Print UNIX time (seconds since Jan 1, 1970, 00:00:00 UTC) | ||
| + | perl -le 'print time' | ||
| + | |||
| + | # Print GMT (Greenwich Mean Time) and local computer time | ||
| + | perl -le 'print scalar gmtime' | ||
| + | perl -le 'print scalar localtime' | ||
| + | |||
| + | # Print local computer time in H:M:S format | ||
| + | perl -le 'print join ":", | ||
| + | |||
| + | # Print yesterday' | ||
| + | perl -MPOSIX -le '@now = localtime; $now[3] -= 1; print scalar localtime mktime @now' | ||
| + | |||
| + | # Print date 14 months, 9 days and 7 seconds ago | ||
| + | perl -MPOSIX -le '@now = localtime; $now[0] -= 7; $now[4] -= 14; $now[7] -= 9; print scalar localtime mktime @now' | ||
| + | |||
| + | # Prepend timestamps to stdout (GMT, localtime) | ||
| + | tail -f logfile | perl -ne 'print scalar gmtime," | ||
| + | tail -f logfile | perl -ne 'print scalar localtime," | ||
| + | |||
| + | # Calculate factorial of 5 | ||
| + | perl -MMath:: | ||
| + | perl -le '$f = 1; $f *= $_ for 1..5; print $f' | ||
| + | |||
| + | # Calculate greatest common divisor (GCM) | ||
| + | perl -MMath:: | ||
| + | |||
| + | # Calculate GCM of numbers 20 and 35 using Euclid' | ||
| + | perl -le '$n = 20; $m = 35; ($m,$n) = ($n,$m%$n) while $n; print $m' | ||
| + | |||
| + | # Calculate least common multiple (LCM) of numbers 35, 20 and 8 | ||
| + | perl -MMath:: | ||
| + | |||
| + | # Calculate LCM of 20 and 35 using Euclid' | ||
| + | perl -le '$a = $n = 20; $b = $m = 35; ($m,$n) = ($n,$m%$n) while $n; print $a*$b/ | ||
| + | |||
| + | # Generate 10 random numbers between 5 and 15 (excluding 15) | ||
| + | perl -le ' | ||
| + | |||
| + | # Find and print all permutations of a list | ||
| + | perl -MAlgorithm:: | ||
| + | |||
| + | # Generate the power set | ||
| + | perl -MList:: | ||
| + | |||
| + | # Convert an IP address to unsigned integer | ||
| + | perl -le '$i=3; $u += ($_<< | ||
| + | perl -le ' | ||
| + | perl -le 'print unpack(" | ||
| + | perl -MSocket -le 'print unpack(" | ||
| + | |||
| + | # Convert an unsigned integer to an IP address | ||
| + | perl -MSocket -le 'print inet_ntoa(pack(" | ||
| + | perl -le '$ip = 2130706433; print join " | ||
| + | perl -le '$ip = 2130706433; $, = " | ||
| + | |||
| + | |||
| + | STRING CREATION AND ARRAY CREATION | ||
| + | ---------------------------------- | ||
| + | |||
| + | # Generate and print the alphabet | ||
| + | perl -le 'print a..z' | ||
| + | perl -le 'print (" | ||
| + | perl -le '$, = ","; | ||
| + | perl -le 'print join ",", | ||
| + | |||
| + | # Generate and print all the strings from " | ||
| + | perl -le 'print (" | ||
| + | perl -le 'print " | ||
| + | |||
| + | # Create a hex lookup table | ||
| + | @hex = (0..9, " | ||
| + | |||
| + | # Convert a decimal number to hex using @hex lookup table | ||
| + | perl -le '$num = 255; @hex = (0..9, " | ||
| + | perl -le '$hex = sprintf(" | ||
| + | perl -le '$num = " | ||
| + | |||
| + | # Generate a random 8 character password | ||
| + | perl -le 'print map { (" | ||
| + | perl -le 'print map { (" | ||
| + | |||
| + | # Create a string of specific length | ||
| + | perl -le 'print " | ||
| + | |||
| + | # Create a repeated list of elements | ||
| + | perl -le '@list = (1,2)x20; print " | ||
| + | |||
| + | # Create an array from a string | ||
| + | @months = split ' ', "Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec" | ||
| + | @months = qw/Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec/ | ||
| + | |||
| + | # Create a string from an array | ||
| + | @stuff = (" | ||
| + | |||
| + | # Find the numeric values for characters in the string | ||
| + | perl -le 'print join ", ", map { ord } split //, "hello world"' | ||
| + | |||
| + | # Convert a list of numeric ASCII values into a string | ||
| + | perl -le ' | ||
| + | perl -le ' | ||
| + | |||
| + | # Generate an array with odd numbers from 1 to 100 | ||
| + | perl -le '@odd = grep {$_ % 2 == 1} 1..100; print " | ||
| + | perl -le '@odd = grep { $_ & 1 } 1..100; print " | ||
| + | |||
| + | # Generate an array with even numbers from 1 to 100 | ||
| + | perl -le '@even = grep {$_ % 2 == 0} 1..100; print " | ||
| + | |||
| + | # Find the length of the string | ||
| + | perl -le 'print length " | ||
| + | |||
| + | # Find the number of elements in an array | ||
| + | perl -le ' | ||
| + | perl -le ' | ||
| + | |||
| + | |||
| + | TEXT CONVERSION AND SUBSTITUTION | ||
| + | -------------------------------- | ||
| + | |||
| + | # ROT13 a string | ||
| + | ' | ||
| + | |||
| + | # ROT 13 a file | ||
| + | perl -lpe ' | ||
| + | |||
| + | # Base64 encode a string | ||
| + | perl -MMIME:: | ||
| + | perl -MMIME:: | ||
| + | |||
| + | # Base64 decode a string | ||
| + | perl -MMIME:: | ||
| + | perl -MMIME:: | ||
| + | |||
| + | # URL-escape a string | ||
| + | perl -MURI:: | ||
| + | |||
| + | # URL-unescape a string | ||
| + | perl -MURI:: | ||
| + | |||
| + | # HTML-encode a string | ||
| + | perl -MHTML:: | ||
| + | |||
| + | # HTML-decode a string | ||
| + | perl -MHTML:: | ||
| + | |||
| + | # Convert all text to uppercase | ||
| + | perl -nle 'print uc' | ||
| + | perl -ple ' | ||
| + | perl -nle 'print " | ||
| + | |||
| + | # Convert all text to lowercase | ||
| + | perl -nle 'print lc' | ||
| + | perl -ple ' | ||
| + | perl -nle 'print " | ||
| + | |||
| + | # Uppercase only the first word of each line | ||
| + | perl -nle 'print ucfirst lc' | ||
| + | perl -nle 'print " | ||
| + | |||
| + | # Invert the letter case | ||
| + | perl -ple ' | ||
| + | |||
| + | # Camel case each line | ||
| + | perl -ple ' | ||
| + | perl -ple ' | ||
| + | |||
| + | # Strip leading whitespace (spaces, tabs) from the beginning of each line | ||
| + | perl -ple 's/^[ \t]+//' | ||
| + | perl -ple ' | ||
| + | |||
| + | # Strip trailing whitespace (space, tabs) from the end of each line | ||
| + | perl -ple 's/[ \t]+$//' | ||
| + | |||
| + | # Strip whitespace from the beginning and end of each line | ||
| + | perl -ple 's/^[ \t]+|[ \t]+$// | ||
| + | |||
| + | # Convert UNIX newlines to DOS/Windows newlines | ||
| + | perl -pe ' | ||
| + | |||
| + | # Convert DOS/Windows newlines to UNIX newlines | ||
| + | perl -pe ' | ||
| + | |||
| + | # Convert UNIX newlines to Mac newlines | ||
| + | perl -pe ' | ||
| + | |||
| + | # Substitute (find and replace) " | ||
| + | perl -pe ' | ||
| + | |||
| + | # Substitute (find and replace) all " | ||
| + | perl -pe ' | ||
| + | |||
| + | # Substitute (find and replace) " | ||
| + | perl -pe '/baz/ && s/ | ||
| + | |||
| + | # Binary patch a file (find and replace a given array of bytes as hex numbers) | ||
| + | perl -pi -e ' | ||
| + | |||
| + | |||
| + | SELECTIVE PRINTING AND DELETING OF CERTAIN LINES | ||
| + | ------------------------------------------------ | ||
| + | |||
| + | # Print the first line of a file (emulate head -1) | ||
| + | perl -ne ' | ||
| + | |||
| + | # Print the first 10 lines of a file (emulate head -10) | ||
| + | perl -ne 'print if $. <= 10' | ||
| + | perl -ne '$. <= 10 && print' | ||
| + | perl -ne 'print if 1..10' | ||
| + | |||
| + | # Print the last line of a file (emulate tail -1) | ||
| + | perl -ne '$last = $_; END { print $last }' | ||
| + | perl -ne 'print if eof' | ||
| + | |||
| + | # Print the last 10 lines of a file (emulate tail -10) | ||
| + | perl -ne 'push @a, $_; @a = @a[@a-10..$# | ||
| + | |||
| + | # Print only lines that match a regular expression | ||
| + | perl -ne '/ | ||
| + | |||
| + | # Print only lines that do not match a regular expression | ||
| + | perl -ne ' | ||
| + | |||
| + | # Print the line before a line that matches a regular expression | ||
| + | perl -ne '/ | ||
| + | |||
| + | # Print the line after a line that matches a regular expression | ||
| + | perl -ne 'if ($p) { print; $p = 0 } $p++ if / | ||
| + | |||
| + | # Print lines that match regex AAA and regex BBB in any order | ||
| + | perl -ne '/AAA/ && /BBB/ && print' | ||
| + | |||
| + | # Print lines that don't match match regexes AAA and BBB | ||
| + | perl -ne ' | ||
| + | |||
| + | # Print lines that match regex AAA followed by regex BBB followed by CCC | ||
| + | perl -ne '/ | ||
| + | |||
| + | # Print lines that are 80 chars or longer | ||
| + | perl -ne 'print if length >= 80' | ||
| + | |||
| + | # Print lines that are less than 80 chars in length | ||
| + | perl -ne 'print if length < 80' | ||
| + | |||
| + | # Print only line 13 | ||
| + | perl -ne '$. == 13 && print && exit' | ||
| + | |||
| + | # Print all lines except line 27 | ||
| + | perl -ne '$. != 27 && print' | ||
| + | perl -ne 'print if $. != 27' | ||
| + | |||
| + | # Print only lines 13, 19 and 67 | ||
| + | perl -ne 'print if $. == 13 || $. == 19 || $. == 67' | ||
| + | perl -ne 'print if int($.) ~~ (13, 19, 67)' | ||
| + | |||
| + | # Print all lines between two regexes (including lines that match regex) | ||
| + | perl -ne 'print if / | ||
| + | |||
| + | # Print all lines from line 17 to line 30 | ||
| + | perl -ne 'print if $. >= 17 && $. <= 30' | ||
| + | perl -ne 'print if int($.) ~~ (17..30)' | ||
| + | perl -ne 'print if grep { $_ == $. } 17..30' | ||
| + | |||
| + | # Print the longest line | ||
| + | perl -ne '$l = $_ if length($_) > length($l); END { print $l }' | ||
| + | |||
| + | # Print the shortest line | ||
| + | perl -ne '$s = $_ if $. == 1; $s = $_ if length($_) < length($s); END { print $s }' | ||
| + | |||
| + | # Print all lines that contain a number | ||
| + | perl -ne 'print if / | ||
| + | |||
| + | # Find all lines that contain only a number | ||
| + | perl -ne 'print if / | ||
| + | |||
| + | # Print all lines that contain only characters | ||
| + | perl -ne 'print if / | ||
| + | |||
| + | # Print every second line | ||
| + | perl -ne 'print if $. % 2' | ||
| + | |||
| + | # Print every second line, starting the second line | ||
| + | perl -ne 'print if $. % 2 == 0' | ||
| + | |||
| + | # Print all lines that repeat | ||
| + | perl -ne 'print if ++$a{$_} == 2' | ||
| + | |||
| + | # Print all unique lines | ||
| + | perl -ne 'print unless $a{$_}++' | ||
| + | |||
| + | # Print the first field (word) of every line (emulate cut -f 1 -d ' ') | ||
| + | perl -alne 'print $F[0]' | ||
| + | |||
| + | |||
| + | HANDY REGULAR EXPRESSIONS | ||
| + | ------------------------- | ||
| + | |||
| + | # Match something that looks like an IP address | ||
| + | / | ||
| + | / | ||
| + | |||
| + | # Test if a number is in range 0-255 | ||
| + | / | ||
| + | |||
| + | # Match an IP address | ||
| + | my $ip_part = qr|([0-9]|[0-9][0-9]|1[0-9][0-9]|2[0-4][0-9]|25[0-5])|; | ||
| + | if ($ip =~ / | ||
| + | say "valid ip"; | ||
| + | } | ||
| + | |||
| + | # Check if the string looks like an email address | ||
| + | / | ||
| + | |||
| + | # Check if the string is a decimal number | ||
| + | /^\d+$/ | ||
| + | / | ||
| + | / | ||
| + | |||
| + | # Check if the string is a hexadecimal number | ||
| + | / | ||
| + | |||
| + | # Check if the string is an octal number | ||
| + | / | ||
| + | |||
| + | # Check if the string is binary | ||
| + | /^[01]+$/ | ||
| + | |||
| + | # Check if a word appears twice in the string | ||
| + | / | ||
| + | |||
| + | # Increase all numbers by one in the string | ||
| + | $str =~ s/ | ||
| + | |||
| + | # Extract HTTP User-Agent string from the HTTP headers | ||
| + | / | ||
| + | |||
| + | # Match printable ASCII characters | ||
| + | /[ -~]/ | ||
| + | |||
| + | # Match unprintable ASCII characters | ||
| + | /[^ -~]/ | ||
| + | |||
| + | # Match text between two HTML tags | ||
| + | m|< | ||
| + | m|< | ||
| + | |||
| + | # Replace all <b> tags with < | ||
| + | $html =~ s|< | ||
| + | |||
| + | # Extract all matches from a regular expression | ||
| + | my @matches = $text =~ /regex/g; | ||
| + | |||
| + | |||
| + | PERL TRICKS | ||
| + | ----------- | ||
| + | |||
| + | # Print the version of a Perl module | ||
| + | perl -MModule -le 'print $Module:: | ||
| + | perl -MLWP:: | ||
| + | |||
| + | |||
| + | PERL ONE-LINERS EXPLAINED E-BOOK | ||
| + | -------------------------------- | ||
| + | |||
| + | I have written an ebook based on the one-liners in this file. If you want to | ||
| + | support my work and learn more about these one-liners, you can get a copy | ||
| + | of my ebook at: | ||
| + | |||
| + | https:// | ||
| + | |||
| + | The ebook is based on the 7-part article series that I wrote on my blog. | ||
| + | In the ebook I reviewed all the one-liners, improved explanations, | ||
| + | new ones, and added two new chapters - introduction to Perl one-liners | ||
| + | and summary of commonly used special variables. | ||
| + | |||
| + | You can read the original article series here: | ||
| + | |||
| + | https:// | ||
| + | https:// | ||
| + | https:// | ||
| + | https:// | ||
| + | https:// | ||
| + | https:// | ||
| + | https:// | ||
| + | |||
| + | |||
| + | CREDITS | ||
| + | ------- | ||
| + | |||
| + | Andy Lester | ||
| + | Shlomi Fish | ||
| + | Madars Virza http:// | ||
| + | caffecaldo | ||
| + | Kirk Kimmel | ||
| + | avar https:// | ||
| + | rent0n | ||
| + | |||
| + | |||
| + | FOUND A BUG? HAVE ANOTHER ONE-LINER? | ||
| + | ------------------------------------ | ||
| + | |||
| + | Email bugs and new one-liners to me at [email protected]. | ||
| + | |||
| + | |||
| + | HAVE FUN | ||
| + | -------- | ||
| + | |||
| + | I hope you found these one-liners useful. Have fun and see ya! | ||
| + | |||
| + | #---end of file--- | ||
| + | </ | ||
| + | |||
| + | ==== Using %ENV to pass parameters to a perl one-liner ==== | ||
| + | Used here to clean up a comma-separated list of parameters passed into a shell. | ||
| + | < | ||
| + | - - remove all spaces | ||
| + | - - remove any quote characters | ||
| + | - - replace , with ',' | ||
| + | - ----------------------------- | ||
| + | SCHEMAE=`export quot="'"; | ||
| + | </ | ||
| + | |||
| + | ==== Add a line after another one in a file using Perl ==== | ||
| + | Use Perl to filter a script (or a load of scripts) and add an extra line when certain pattern match condition exists.\\ | ||
| Uses -n switch with print because using -p switch evaluates your condition first and **then** prints the line. This could be used if you want to print a line **before** the matched line! | Uses -n switch with print because using -p switch evaluates your condition first and **then** prints the line. This could be used if you want to print a line **before** the matched line! | ||
| - | < | + | < |
| + | for commvaulthost in ci00031669-hn491 ci00031670-hn492 ci00031671-hn5407 ci00031672-hn364 ci00031673-hn5207 ci00031674-hn5217; | ||
| + | unixhost=$(echo ${commvaulthost} | awk -F\\- ' | ||
| + | perl -n -i -e ' | ||
| + | done | ||
| + | </ | ||
| - | =====perl -a===== | + | ==== perl -a ==== |
| - | Turns on autosplit mode. Use -F< | + | Turns on autosplit mode. Use -F< |
| Breaks down the input into elements of an automatically assigned array called @F. | Breaks down the input into elements of an automatically assigned array called @F. | ||
| - | < | + | < |
| + | perl -F: -lane 'print $F[0]' / | ||
| + | </ | ||
| - | =====perl -l===== | + | ==== perl -l ==== |
| - | When trimming whitespace from your input, the \n is removed also. Using -l adds it back in at the end of processing.<br /> | + | When trimming whitespace from your input, the \n is removed also. Using -l adds it back in at the end of processing.\\ |
| See examples above. | See examples above. | ||
| - | =====BEGIN and END===== | + | ==== BEGIN and END ==== |
| - | Allows you to run code before or after the loop over the lines.<br /> | + | Allows you to run code before or after the loop over the lines.\\ |
| - | Example, sum the values in the second column of a CSV file...<br /> | + | Example, sum the values in the second column of a CSV file...\\ |
| Replace the ' | Replace the ' | ||
| - | < | + | < |
| + | perl -F, -lane '$sum += $F[1]; END { print $sum }' somefile.csv | ||
| + | </ | ||
| - | =====.. operater===== | + | ==== .. operater ==== |
| Cut chunks out of a file from /start range marker/ .. /end range marker/ | Cut chunks out of a file from /start range marker/ .. /end range marker/ | ||
| - | < | + | < |
| + | perl -ne 'print if /-----BEGIN PGP PUBLIC KEY BLOCK-----/ | ||
| + | </ | ||
| - | =====A one-liner web server!===== | + | ==== A one-liner web server! ==== |
| - | < | + | < |
| - | * First we accept a socket and fork the server. Then we overload the new socket as a code ref. This code ref takes one argument, another code ref, which is used as a callback. | + | perl -MIO::All -e ' |
| - | * The callback is called once for every line read on the socket. The line is put into $_ and the socket itself is passed in to the callback. | + | </ |
| - | * Our callback is scanning the line in $_ for an HTTP GET request. If one is found it parses the file name into $1. Then we use $1 to create an new IO::All file object... with a twist. If the file is executable(" | + | * First we accept a socket and fork the server. Then we overload the new socket as a code ref. This code ref takes one argument, another code ref, which is used as a callback. |
| - | * Whatever the resulting object is, we direct the contents back at our socket which is in $_[[0]]. | + | * The callback is called once for every line read on the socket. The line is put into $_ and the socket itself is passed in to the callback. |
| + | * Our callback is scanning the line in $_ for an HTTP GET request. If one is found it parses the file name into $1. Then we use $1 to create an new IO::All file object... with a twist. If the file is executable(" | ||
| + | * Whatever the resulting object is, we direct the contents back at our socket which is in $_[0]. | ||
| From: [[http:// | From: [[http:// | ||
| - | =====What Perl modules are installed?===== | + | ==== Print out all the environment variables on a Perl web server ==== |
| + | This can be used as a test status page to see if the cgi-bin directory is working properly. And that Perl is processing the files correctly. | ||
| + | < | ||
| + | #!perl | ||
| + | |||
| + | print " | ||
| + | print "< | ||
| + | |||
| + | foreach (sort keys %ENV) { | ||
| + | print "< | ||
| + | } | ||
| + | |||
| + | 1; | ||
| + | </ | ||
| + | or | ||
| + | < | ||
| + | #!perl | ||
| + | |||
| + | use HTML:: | ||
| + | use CGI qw(header); | ||
| + | |||
| + | $q = new CGI; | ||
| + | print $q-> | ||
| + | |||
| + | print "< | ||
| + | print "< | ||
| + | print "</ | ||
| + | |||
| + | $p = new HTML:: | ||
| + | $p-> | ||
| + | $p-> | ||
| + | $p-> | ||
| + | $p-> | ||
| + | </ | ||
| + | |||
| + | ==== Retrieve a file from an authenticated website using Perl ==== | ||
| + | This site ([[https:// | ||
| + | |||
| + | Call your modules | ||
| + | < | ||
| + | # | ||
| + | use strict; use warnings; | ||
| + | |||
| + | use LWP; | ||
| + | use HTTP:: | ||
| + | use HTTP:: | ||
| + | use File::Path qw{mkpath}; | ||
| + | </ | ||
| + | The modules HTTP:: | ||
| + | |||
| + | Check your temporary path: | ||
| + | < | ||
| + | my $HOME = $ENV{HOME} . '/ | ||
| + | mkpath $HOME | ||
| + | </ | ||
| + | We will need this location to save our cookie jar file and the file we want to download | ||
| + | |||
| + | Create a cookie jar and a LWP user-agent: | ||
| + | < | ||
| + | # create a cookie jar on disk | ||
| + | my $cookies = HTTP:: | ||
| + | file => $HOME.'/ | ||
| + | autosave => 1, | ||
| + | ); | ||
| + | |||
| + | # create an user-agent and assign the cookie jar to it | ||
| + | my $http = LWP:: | ||
| + | $http-> | ||
| + | </ | ||
| + | No rocket science here, just create the objects! | ||
| + | |||
| + | Send the authentication request: | ||
| + | < | ||
| + | # try to log in | ||
| + | my $login = $http-> | ||
| + | ' | ||
| + | username => ' | ||
| + | password => ' | ||
| + | ); | ||
| + | </ | ||
| + | Once authenticated, | ||
| + | From this point on, it is required to check whether the log in succeeded and then continue with downloading the file. If the log in failed, an error message should be displayed with the reason on the failure. | ||
| + | |||
| + | < | ||
| + | # check if log in succeeded | ||
| + | if($login-> | ||
| + | print "- logged in successfully\n"; | ||
| + | print "- requesting file, might take a while\n"; | ||
| + | |||
| + | # make request to download the file | ||
| + | my $url = ' | ||
| + | my $file_req | ||
| + | my $get_file | ||
| + | |||
| + | # check request status | ||
| + | if($get_file-> | ||
| + | print " | ||
| + | |||
| + | # save the file content to disk | ||
| + | open my $fh, '>', | ||
| + | or die " | ||
| + | print $fh $get_file-> | ||
| + | close $fh; | ||
| + | |||
| + | print " | ||
| + | print " | ||
| + | print " | ||
| + | print " | ||
| + | } | ||
| + | else { | ||
| + | die " | ||
| + | } | ||
| + | } | ||
| + | else { | ||
| + | die " | ||
| + | } | ||
| + | </ | ||
| + | |||
| + | |||
| + | ==== What Perl modules are installed? ==== | ||
| As found by typing " | As found by typing " | ||
| - | < | + | < |
| - | =====Prepend a line at the beginning of a file===== | + | # |
| + | use File:: | ||
| + | my @files; | ||
| + | find( | ||
| + | sub { | ||
| + | push @files, $File:: | ||
| + | if -f $File:: | ||
| + | }, | ||
| + | @INC | ||
| + | ); | ||
| + | print join " | ||
| + | </ | ||
| + | ==== Prepend a line at the beginning of a file ==== | ||
| Surprisingly tricky thing to do as a one-liner. Seemingly cannot be done (cross-platform) in ksh in one line. | Surprisingly tricky thing to do as a one-liner. Seemingly cannot be done (cross-platform) in ksh in one line. | ||
| - | < | + | < |
| + | perl -p -i -e 'print "This is line 1 now!\n" | ||
| + | </ | ||
| - | =====Implement a socket client/ | + | ==== Implement a socket client/ |
| [[http:// | [[http:// | ||
| - | =====Scan for emails with attachments and save attachments to files===== | + | ==== Scan for emails with attachments and save attachments to files ==== |
| - | * [[https:// | + | * [[https:// |
| - | =====Install a Perl module from CPAN===== | + | ==== Install a Perl module from CPAN ==== |
| - | < | + | < |
| + | perl -MCPAN -e ' | ||
| + | </ | ||
| - | =====Print out the first and last words of all lines in a file===== | + | ==== Print out the first and last words of all lines in a file ==== |
| - | <code> | + | < |
| - | =====Print only the lines in a file between 2 search patterns===== | + | perl -ae 'print " |
| - | < | + | </ |
| - | =====Mass update of files using perl inline script===== | + | ==== Mass update of files using perl inline script ==== |
| - | < | + | < |
| + | for server in $(cat / | ||
| + | ssh $server "perl -p -i -e ' | ||
| + | done | ||
| + | </ | ||
| - | =====Perl emulation of dos2unix command===== | + | ==== Perl emulation of dos2unix command ==== |
| - | < | + | < |
| + | perl -p -i -e ' | ||
| + | </ | ||
| and then back again with unix2dos | and then back again with unix2dos | ||
| - | < | + | < |
| + | perl -p -i -e ' | ||
| + | </ | ||
| - | =====Print a file except / excluding certain lines===== | + | ==== Print a file except / excluding certain lines ==== |
| - | < | + | < |
| + | perl -ne 'next if (/ | ||
| + | </ | ||
| - | =====Exclude the first few lines of a file===== | + | ==== Difference between double dot and triple dot operator ==== |
| - | < | + | They can both work as flip-flop operators. The double dot will check the second pattern if it is on the same line as the first. For the triple dot to work, the end pattern must be on a different line from the begin pattern.\\ |
| - | =====Delete the last line of a file===== | + | Explained better [[https:// |
| - | < | + | |
| - | =====Print lines between 2 markers | + | ==== Exclude the first few lines of a file ==== |
| - | < | + | < |
| - | =====Print lines not between 2 markers in a file!===== | + | perl -ne 'print unless 1 .. 10' filename |
| - | < | + | </ |
| - | =====Print a few lines in a file===== | + | ==== Print lines between 2 markers in a file ==== |
| - | < | + | < |
| + | perl -ne 'print if /START/ .. / | ||
| + | </ | ||
| + | ==== Print only the lines in a file between 2 search patterns (exclusive of the markers) | ||
| + | < | ||
| + | perl -ne 'print if /pattern1/ ... /pattern2/ and !/pattern1/ and !/ | ||
| + | </ | ||
| + | ==== Print lines not between 2 markers in a file! ==== | ||
| + | < | ||
| + | perl -ne 'print unless /START/ .. / | ||
| + | </ | ||
| + | ==== Delete the last line of a file ==== | ||
| + | < | ||
| + | perl -e '@x=<>; pop(@x); print @x' | ||
| + | </ | ||
| + | ==== Print a few lines in a file ==== | ||
| + | < | ||
| + | perl -ne 'print if 15 .. 17' | ||
| + | </ | ||
| but more efficiently... | but more efficiently... | ||
| - | < | + | < |
| - | =====Print lines of a file in reverse order===== | + | perl -ne 'print if $. >= 15; exit if $. >= 17;' |
| - | < | + | </ |
| - | =====Print characters in lines of a file in reverse order===== | + | ==== Print lines of a file in reverse order ==== |
| - | < | + | < |
| - | =====Find palindromes in a file===== | + | perl -e 'print reverse <>' |
| - | < | + | </ |
| - | =====Reverse all the characters in a file===== | + | ==== Print characters in lines of a file in reverse order ==== |
| - | < | + | < |
| - | =====Reverse all the characters in a paragraph but keeping the paragraphs in order===== | + | perl -nle 'print scalar reverse $_' filename |
| - | < | + | </ |
| - | =====Trim all heading and trailing spaces and compress any intermediate spaces to 1===== | + | ==== Find palindromes in a file ==== |
| - | < | + | < |
| - | =====Nice one to reformat a document so that all lines are between 50 and 70 characters long. Only breaks on whitespace===== | + | perl -lne '$_ = lc; print if $_ eq reverse' |
| - | < | + | </ |
| + | ==== Reverse all the characters in a file ==== | ||
| + | < | ||
| + | perl -0777e 'print scalar reverse <>' | ||
| + | </ | ||
| + | ==== Reverse all the characters in a paragraph but keeping the paragraphs in order ==== | ||
| + | < | ||
| + | perl -00 -e 'print reverse <>' | ||
| + | </ | ||
| + | ==== Trim all heading and trailing spaces and compress any intermediate spaces to 1 ==== | ||
| + | < | ||
| + | perl -pe '$_ = " $_ "; tr/ \t/ /s; $_ = substr($_, | ||
| + | </ | ||
| + | ==== Nice one to reformat a document so that all lines are between 50 and 70 characters long. Only breaks on whitespace ==== | ||
| + | < | ||
| + | perl -000 -p -e 'tr/ \t\nr/ /; | ||
| + | </ | ||
| - | =====Substitute text in subject placing | + | ==== Assign |
| - | Variable " | + | I aways forget the syntax for this so hopefully I will find this next time I need it! |
| - | < | + | < |
| + | ($result = $subject) =~ s/ | ||
| + | </ | ||
| - | =====Print balancing quotes===== | + | ==== Print balancing quotes ==== |
| - | < | + | < |
| - | =====Capitalise all words in a file (ensuring all others letters in the words are lower case)===== | + | perl -ne ' |
| + | </ | ||
| + | ==== Capitalise all words in a file (ensuring all others letters in the words are lower case) ==== | ||
| ref: [[http:// | ref: [[http:// | ||
| - | < | + | < |
| - | =====Translate into Zafir language!===== | + | perl -pe ' |
| - | < | + | </ |
| + | ==== Translate into Zafir language! ==== | ||
| + | < | ||
| + | perl -pe ' | ||
| + | </ | ||
| - | =====Read in (include) a configuration file in Perl===== | + | ==== Read in (include) a configuration file in Perl ==== |
| - | Although there are several ways to " | + | Although there are several ways to " |
| - | The problem with using require or include is that the scope is different so any my variables won't be visible<br /> | + | The problem with using require or include is that the scope is different so any my variables won't be visible\\ |
| The trick here is the use of the " | The trick here is the use of the " | ||
| - | < | + | < |
| + | # ==================== | ||
| + | # bring in config file | ||
| + | # ==================== | ||
| + | our %config; | ||
| + | open (CONFIG, "< | ||
| + | while (< | ||
| + | chomp; s/#.*//; s/^\s+//; s/\s+$//; | ||
| + | next unless /=/; | ||
| + | my ($var, $value) = split(/ | ||
| + | $config{$var} = $value; | ||
| + | } | ||
| + | close CONFIG; | ||
| + | </ | ||
| - | =====Send an email from perl without needing any external modules===== | + | ==== Send an email from perl without needing any external modules ==== |
| - | but it only works on Unix :( | + | but it only works on Unix |
| - | < | + | < |
| + | # Simple Email Function | ||
| + | # ($to, $from, $subject, $message) | ||
| + | sub sendemail | ||
| + | { | ||
| + | my ($to, $from, $subject, $message) = @_; | ||
| + | my $sendmail = '/ | ||
| + | open(MAIL, " | ||
| + | print MAIL "From: $from\n"; | ||
| + | print MAIL "To: $to\n"; | ||
| + | print MAIL " | ||
| + | print MAIL " | ||
| + | close(MAIL); | ||
| + | } | ||
| + | </ | ||
| Using the function is straightforward. Simply pass it the data in the correct order. | Using the function is straightforward. Simply pass it the data in the correct order. | ||
| - | < | + | < |
| - | =====What "day of the year" (DOY) number was it yesterday?===== | + | sendemail ( " |
| - | < | + | </ |
| - | =====What "day of the year" (DOY) number is it today?===== | + | ==== What "day of the year" (DOY) number was it yesterday? ==== |
| - | < | + | < |
| + | YESTERDAY=`perl -e 'print sub{$_[7]}-> | ||
| + | </ | ||
| + | ==== What "day of the year" (DOY) number is it today? ==== | ||
| + | < | ||
| + | TODAY=`perl -e 'print sub{$_[7]}-> | ||
| + | </ | ||
| - | =====Sort a list===== | + | ==== Sort a list ==== |
| - | * [[http:// | + | * [[http:// |
| - | * [[http:// | + | * [[http:// |
| - | * [[http:// | + | * [[http:// |
| Numerically | Numerically | ||
| - | < | + | < |
| + | @sorted = sort { $a <=> $b } @unsorted | ||
| + | </ | ||
| Alphabetically | Alphabetically | ||
| - | < | + | < |
| + | @sorted = sort { $a cmp $b } @unsorted | ||
| + | </ | ||
| Alphabetically (case-insensitive) | Alphabetically (case-insensitive) | ||
| - | < | + | < |
| + | @sorted = sort { lc($a) cmp lc($b) } @unsorted | ||
| + | </ | ||
| Schwartzian transform | Schwartzian transform | ||
| - | < | + | < |
| + | my @quickly_sorted_files = | ||
| + | map { $_->[0] } | ||
| + | sort { $a->[1] <=> $b->[1] } | ||
| + | map { [$_, -s $_] } | ||
| + | | ||
| + | </ | ||
| broken down into (semi)understandable pieces looks like this... | broken down into (semi)understandable pieces looks like this... | ||
| - | < | + | < |
| + | my @unsorted_pairs = map { [$_, -s $_] } @files; | ||
| + | my @sorted_pairs = sort { $a->[1] <=> $b->[1] } @unsorted_pairs; | ||
| + | my @quickly_sorted_files = map { $_->[0] } @sorted_pairs; | ||
| + | </ | ||
| - | =====Use ' | + | ==== Use ' |
| - | * http:// | + | * http:// |
| - | Push the list in one side (right) and get it back on the other (left) with some transformation applied.<br /> | + | Push the list in one side (right) and get it back on the other (left) with some transformation applied.\\ |
| Inside the code block, you refer to the current element with the traditional $_ variable. | Inside the code block, you refer to the current element with the traditional $_ variable. | ||
| - | < | + | < |
| + | my @langs = qw(perl php python); | ||
| + | my @langs = map { uc($_) } @langs; | ||
| + | Result: PERL PHP PYTHON | ||
| + | </ | ||
| Use it with join to create clever stuff... | Use it with join to create clever stuff... | ||
| - | < | + | < |
| + | sub make_query_string { | ||
| + | my ( $vals ) = @_; | ||
| + | | ||
| + | } | ||
| + | my %query_params = ( | ||
| + | a => 1, | ||
| + | b => 2, | ||
| + | c => 3, | ||
| + | d => 4, | ||
| + | ); | ||
| + | my $query_string = make_query_string(\%query_params); | ||
| + | Result: & | ||
| + | </ | ||
| - | =====Difference in hours between two dates===== | + | ==== Difference in hours between two dates ==== |
| - | < | + | < |
| + | use Time:: | ||
| + | use DateTime:: | ||
| + | |||
| + | my $parser = DateTime:: | ||
| + | pattern | ||
| + | locale | ||
| + | on_error => ' | ||
| + | ); | ||
| + | my $timethen = $parser-> | ||
| + | my $timenow | ||
| + | my $timediff = $timenow-> | ||
| + | |||
| + | print ('< | ||
| + | </ | ||
| or, without using any external modules... | or, without using any external modules... | ||
| - | <code> | + | < |
| - | =====Slurp an external file into a variable===== | + | my ($host, |
| - | The idea is to read an SQL file into a variable to prepare and execute it< | + | |
| - | =====Search for a (list of) keyword(s) in a file===== | + | # ---------------------------- |
| + | # work out how old the file is | ||
| + | # ---------------------------- | ||
| + | my $timenow | ||
| + | my $difference = $timenow - $timethen; | ||
| + | my $hours | ||
| + | $difference | ||
| + | my $mins = $difference/ | ||
| + | my $secs = $difference - ($mins*60); | ||
| + | </ | ||
| + | |||
| + | ==== Slurp an external file into a variable ==== | ||
| + | The idea is to read an SQL file into a variable to prepare and execute it< | ||
| + | # | ||
| + | use strict; | ||
| + | my $stmt; | ||
| + | my $quoted_stmt; | ||
| + | $quoted_stmt = 7; | ||
| + | open (FH,"<"," | ||
| + | local $/ = undef; | ||
| + | $stmt = < | ||
| + | close FH; | ||
| + | $quoted_stmt = eval(' | ||
| + | print $quoted_stmt." | ||
| + | </ | ||
| + | |||
| + | ==== Search for a (list of) keyword(s) in a file ==== | ||
| Could write this in several loops but here is a very neat way. Spotted on [[http:// | Could write this in several loops but here is a very neat way. Spotted on [[http:// | ||
| - | < | + | < |
| - | basically it builds up a regular expression and searches for it.<br /> | + | # |
| - | See reference link for more details.<br /><br /> | + | use strict; |
| - | Can also be done very neatly with grep in shell<br /> | + | use warnings; |
| - | < | + | |
| + | # Lexical variable for filehandle is preferred, and always error check opens. | ||
| + | open my $keywords, | ||
| + | open my $search_file, | ||
| + | |||
| + | my $keyword_or = join ' | ||
| + | my $regex = qr|\b($keyword_or)\b|; | ||
| + | |||
| + | while (< | ||
| + | { | ||
| + | while (/ | ||
| + | { | ||
| + | print "$.: $1\n"; | ||
| + | } | ||
| + | } | ||
| + | </ | ||
| + | basically it builds up a regular expression and searches for it. \\ | ||
| + | See reference link for more details.\<br /> | ||
| + | Can also be done very neatly with grep in shell | ||
| + | < | ||
| + | grep -n -f keywords.txt filewithlotsalines.txt | ||
| + | </ | ||
| where keywords.txt is a file containing the list of words to search for. | where keywords.txt is a file containing the list of words to search for. | ||
| - | =====Assign and substitute a value to a variable in one statement===== | + | ==== Assign and substitute a value to a variable in one statement ==== |
| - | Keep forgetting where the parentheses go so have to write it down…<br /> | + | Keep forgetting where the parentheses go so have to write it down…\\ |
| Have to pre-define the variable $new_var otherwise you will get: | Have to pre-define the variable $new_var otherwise you will get: | ||
| - | < | + | < |
| + | Can't declare scalar assignment in " | ||
| + | </ | ||
| - | < | + | < |
| + | ($new_var = $old_var) =~ s/ | ||
| + | </ | ||
| + | or is this what you wanted :-) | ||
| + | < | ||
| + | my $sgasizes=" | ||
| + | my $currsga; | ||
| + | ($currsga) = $sgasizes =~ m/ | ||
| + | print " | ||
| - | =====Match a regular expression across multiple lines===== | + | SGA:343 |
| - | * [[http:// | + | </ |
| + | ==== Match a regular expression across multiple lines ==== | ||
| + | * [[http:// | ||
| I always forget this regex and it's sooo useful! | I always forget this regex and it's sooo useful! | ||
| - | < | + | < |
| + | perl -00 -ne 'print "$1 - $2\n" | ||
| + | </ | ||
| where backup.ini looks like this: | where backup.ini looks like this: | ||
| - | < | + | < |
| + | " | ||
| + | EXP_ZIP_DUMPS=" | ||
| + | ;; | ||
| - | =====Using /s and /m modifiers in a regular expression===== | + | " |
| + | EXP_FLASHBACK=" | ||
| + | RMAN_RECOVERY_WINDOW=5 | ||
| + | RMAN_HOURS_TO_KEEP_ARCHIVES_ON_DISK=48 | ||
| + | EXP_NUM_PARALLEL_WORKERS=16 | ||
| + | ;; | ||
| + | |||
| + | " | ||
| + | RMAN_RECOVERY_WINDOW=10 | ||
| + | RMAN_HOURS_TO_KEEP_ARCHIVES_ON_DISK=48 | ||
| + | EXP_NUM_PARALLEL_WORKERS=5 | ||
| + | ;; | ||
| + | |||
| + | " | ||
| + | RMAN_RECOVERY_WINDOW=15 | ||
| + | ;; | ||
| + | |||
| + | " | ||
| + | RMAN_RECOVERY_WINDOW=20 | ||
| + | ;; | ||
| + | |||
| + | " | ||
| + | RMAN_RECOVERY_WINDOW=25 | ||
| + | RMAN_HOURS_TO_KEEP_ARCHIVES_ON_DISK=48 | ||
| + | ;; | ||
| + | </ | ||
| + | |||
| + | ==== Using /s and /m modifiers in a regular expression ==== | ||
| Tom Christiansen in his [[https:// | Tom Christiansen in his [[https:// | ||
| - | < | + | < |
| + | $/ = //; # paragraph read mode for readline access | ||
| + | while (< | ||
| + | while (m# | ||
| + | # /m makes ^ match near newlines | ||
| + | print "chunk $. in $ARGV has << | ||
| + | } | ||
| + | } | ||
| + | </ | ||
| - | =====Match regular expression and assign to a variable in a single step===== | + | ==== Match regular expression and assign to a variable in a single step ==== |
| - | < | + | < |
| + | $started = $1 if $stmt =~ /Export started at (\d+)/; | ||
| + | </ | ||
| or split directory and filenames (on Windows or Unix) | or split directory and filenames (on Windows or Unix) | ||
| - | < | + | < |
| + | ($dirname, | ||
| + | </ | ||
| or split a line into bits and assign the bits to variables | or split a line into bits and assign the bits to variables | ||
| - | < | + | < |
| + | my ($host, | ||
| + | </ | ||
| - | =====Perl ternary operator===== | + | ==== Perl ternary operator ==== |
| - | Putting examples here as I keep forgetting the syntax/ | + | Putting examples here as I keep forgetting the syntax/ |
| Theoretically it should be: | Theoretically it should be: | ||
| - | < | + | < |
| + | condition ? evaluate_if_condition_was_true : evaluate_if_condition_was_false | ||
| + | </ | ||
| which to me means: | which to me means: | ||
| - | < | + | < |
| + | ($type == ' | ||
| + | </ | ||
| but it's not like that, it's like this: | but it's not like that, it's like this: | ||
| - | < | + | < |
| + | $age_alert = ($type == ' | ||
| + | </ | ||
| and this | and this | ||
| - | < | + | < |
| + | print "< | ||
| + | </ | ||
| - | =====Extract a value from a comma separated list of values in Perl===== | + | ==== Extract a value from a comma separated list of values in Perl ==== |
| Suppose you need the 10th column …but only from the lines ending in ' | Suppose you need the 10th column …but only from the lines ending in ' | ||
| - | < | + | < |
| + | / | ||
| + | </ | ||
| or | or | ||
| - | < | + | < |
| + | $input =~ /detail$/ && my @fields = split(/,/, $input); | ||
| + | </ | ||
| and print out the 10th element of @fields | and print out the 10th element of @fields | ||
| - | =====Typical filter program (without needing to slurp)===== | + | ==== Typical filter program (without needing to slurp) ==== |
| Keep one of these here to save me looking it up all the time! | Keep one of these here to save me looking it up all the time! | ||
| - | < | + | < |
| + | - !/ | ||
| + | |||
| + | use strict; | ||
| + | use warnings; | ||
| + | |||
| + | my $filename = " | ||
| + | open (my $input, '<', | ||
| + | |||
| + | my $count; | ||
| + | |||
| + | while ( my $line = < | ||
| + | my @words = grep { /X/ } split /\b/, $line; | ||
| + | $count += @words; | ||
| + | print join(', | ||
| + | } | ||
| + | |||
| + | print " | ||
| + | |||
| + | __END__ | ||
| + | </ | ||
perl.1544130327.txt.gz · Last modified: 2018/12/06 21:05 by 91.177.234.129
