How to trim the last part of string using Perl? - perl

I need to trim the last part of the string here. The string i have is : abc|bcd|cde|.
I need to get rid of the last |... The trim() command is not helping for some reason may be i am using it wrong, please help... thank you.

This can be done with a simple substitution.
my $string = "abc|bcd|cde|";
$string =~ s/\|$//;

Use chop:
my $string = "abc|bcd|cde|";
chop($string);
say $string;
output:
abc|bcd|cde
From the doc:
Chops off the last character of a string and returns the character
chopped. It is much more efficient than s/.$//s because it neither
scans nor copies the string. If VARIABLE is omitted, chops $_ . If
VARIABLE is a hash, it chops the hash's values, but not its keys.

Related

Inserting newline between matched text is overwriting

I have a text file. I am trying to search for a comma followed by a date, like ",08/18/2014".
It looks like my code finds it, but it replaces it with a comma and a new line and removes everything after it.
if ($firstline =~ s|\,(\d{2}\/.*)|\,\n|g){
print "$firstline";
How do I add a new line between the comma and the date and not remove my text and date?
Thanks.
You can reference your capture groups in your replace expression. I also expanded the regular expression to match the date exactly:
if ($firstline =~ s|,(\d{2}-\d{2}-\d{4})|,\n$1|g) {
print "$firstline\n";
}
Using look ahead/behind:
s|(?<=,)(?=\d{2}\/)|\n|g
or
s|,\K(?=\d{2}\/)|\n|g # Probably faster, but requires 5.10+
Similar to Hunter's answer, without the extended regex, like so:
(Oh, and I don't think you need the backslash before the comma):
$firstline = "hello world ,10/20/1987, sounds great to me"; # testing...
if ($firstline =~ s|,(\d{2}/)|,\n$1|g){
print "$firstline";
}
output:
hello world ,
10/20/1987, sounds great to me

Why does split not return anything?

I am trying to get that Perl split working for more than 2 hours. I don't see an error. Maybe some other eyes can look at it and see the issue. I am sure its a silly one:
#versionsplit=split('.',"15.0.3");
print $versionsplit[0];
print $versionsplit[1];
print $versionsplit[2];
I just get an empty array. Any idea why?
You need:
#versionsplit=split(/\./,"15.0.3");
The first argument to split is a regular expression, not a string. And . is the regex symbol which means ‘match any character’. So all the characters in your input string were being treated as separators, and split wasn't finding anything between them to return.
the "." represents any character.You need to escape it for split function to recognise as a field separator.
change your line to
#versionsplit=split('\.',"15.0.3");

Split by dot using Perl

I use the split function by two ways. First way (string argument to split):
my $string = "chr1.txt";
my #array1 = split(".", $string);
print $array1[0];
I get this error:
Use of uninitialized value in print
When I do split by the second way (regular expression argument to split), I don't get any errors.
my #array1 = split(/\./, $string); print $array1[0];
My first way of splitting is not working only for dot.
What is the reason behind this?
"\." is just ., careful with escape sequences.
If you want a backslash and a dot in a double-quoted string, you need "\\.". Or use single quotes: '\.'
If you just want to parse files and get their suffixes, better use the fileparse() method from File::Basename.
Additional details to the information provided by Mat:
In split "\.", ... the first parameter to split is first interpreted as a double-quoted string before being passed to the regex engine. As Mat said, inside a double-quoted string, a \ is the escape character, meaning "take the next character literally", e.g. for things like putting double quotes inside a double-quoted string: "\""
So your split gets passed "." as the pattern. A single dot means "split on any character". As you know, the split pattern itself is not part of the results. So you have several empty strings as the result.
But why is the first element undefined instead of empty? The answer lies in the documentation for split: if you don't impose a limit on the number of elements returned by split (its third argument) then it will silently remove empty results from the end of the list. As all items are empty the list is empty, hence the first element doesn't exist and is undefined.
You can see the difference with this particular snippet:
my #p1 = split "\.", "thing";
my #p2 = split "\.", "thing", -1;
print scalar(#p1), ' ', scalar(#p2), "\n";
It outputs 0 6.
The "proper" way to deal with this, however, is what #soulSurfer2010 said in his post.

difference between string representation and value in perl

I am puzzled at the following difference.
$str="\xd6\xd0";
decode("GBK",$str);
vs.
$str="d6d0";
#list=map "\\x".$_,unpack("(a2)*", $str);
$str=join "", #list;
decode("GBK",$str);
Why in the first case, it worked to print out the character, while in the second case, it is not working? How can I make it to work in the latter case?
Many thanks.
If you're trying to turn "d6d0" into "\xd6\xd0", you want pack 'H*':
my $str = "d6d0";
$str = pack('H*', $str);
decode("GBK",$str);
join does not interpret escape sequences, it just concatenates strings.
In the first case, the parser interprets the escape sequences and builds a string that is two bytes long. In the second case, you are creating a string that is eight characters:
\xd6\xd0. You probably want to unpack like you are doing, but without prepending the \x, and then use pack with template (H2)* instead of join to put it all together.

Removing quotes from string

So I thought this would just be a simple issue however I'm getting the incorrect results. Basically I am trying to remove the quotes around a string. For example I have the string "01:00" and I want 01:00, below is the code on how I thought I would be able to do this:
$expected_start_time = $conditions =~ m/(\"[^\"])/;
Every time this runs it returns 1, so I'm guessing that it is just returning true and not actually extracting the string from the quotes. This happen no matter what is in the quotes "02:00", "02:20", "08:00", etc.
All you forgot was parens for the LHS to put the match into list context so it returns the submatch group(s). The normal way to do this is:
($expected_start_time) = $condition =~ /"([^"]*)"/;
It appears that you know that the first and last character are quotes. If that is the case, use
$expected_start_time = substr $conditions, 1, -1;
No need for a regexp.
The brute force way is:
$expected_start_time = $conditions;
$expected_start_time =~ s/"//g;
Note that the original regex:
m/(\"[^\"])/
would capture the opening quote and the following non-quote character. To capture the non-quote characters between double quotes, you'd need some variant on:
m/"([^"]*)"/;
This being Perl (and regexes), TMTOWTDI - There's More Than One Way Do It.
In scalar context a regex returns true if the regex matches the string. You can access the match with $1. See perlre.