Making the most possible sentences from multiple synonyms - php

I would like to the most possible different sentences from multiple block of words, in php. For example i put in the php code:
"today" "yesturday" | "is" "is not" | "monday" "tuesday"
It would become:
today is monday
yesturday is monday
today is not tuesday
yesturday is tuesday
etc...
How can i create this in php?
Thank you.

Try this
$block1 = array("today", "yesturday" );
$block2 = array("is", "is not");
$block3 = array("monday", "tuesday");
foreach($block1 as $word1) {
foreach($block2 as $word2) {
foreach($block3 as $word3) {
echo $word1.' '.$word2.' '.$word3."\n";
}
}
}

Related

regex match cond1 OR match cond2 in single command

I need to check if entered date is between 2019-09-01 - 2019-12-31
I can do this as follows: $koodi is user input
$pattern1 = "/^2019-(09|11)-([0-2][0-9]|30)$/";
$pattern2 = "/^2019-(10|12)-([0-2][0-9]|3[0-1])$/";
if(preg_match($pattern1, $koodi) || preg_match($pattern2, $koodi)) {
echo "<code>$koodi</code> ok!<br>\n";
}
else {
echo ("<code>$koodi</code> NOT ok!<br>\n");
}
I was trying to make those two conditions into single regex statement, is that possible and if so how?
I tried:
$pattern = "/^2019-(09|11)-([0-2][0-9]|30)$ | ^2019-(10|12)-([0-2][0-9]|3[0-1])$/";
Did not work, neither the following where i tried to put parentheses around conditions:
$pattern = "/(^2019-(09|11)-([0-2][0-9]|30)$) | (^2019-(10|12)-([0-2][0-9]|3[0-1])$)/";
Please don't use a regex to do that, what if the dates change or what if the next developer has to come and work on this and figure out what your doing?
According to this article you can check if a date is between 2 dates by doing something like this.
<?php
$currentDate = date('Y-m-d');
$currentDate = date('Y-m-d', strtotime($currentDate));
$startDate = date('Y-m-d', strtotime("01/09/2019"));
$endDate = date('Y-m-d', strtotime("01/10/2019"));
if (($currentDate >= $startDate) && ($currentDate <= $endDate)){
echo "Current date is between two dates";
}else{
echo "Current date is not between two dates";
}
as for why your patterns didn't work its because you have a space around the pipe in the middle and you may possibly need to wrap the whole thing in brackets. You also have the $ half way through the regex which is matching the whole string, I would usually only have it at the end, like this: -
^(regex1|regex2)$
I haven't written the correct version in case your tempted to use it, (please use the date objects method)

Need some assistence with Regex (PHP)

I'd like to parse txt files to HTML using preg_replace to add formatting.
The format of the file is like this :
09:19:49 13-12-15 Sunday Hello World
1234567 Today is a beautiful day
1234568 Tomorrow will be even better
1234569 December is the best month of the year!
This should be treated as a group and parsed into a table, like :
<table>
<tr><td>09:19:49 13-12-15</td><td>Sunday</td><td>Hello World</td></tr>
<tr><td>1234567</td><td>(optional)</td><td>Today is a beautiful day</td></tr>
<tr><td>1234568</td><td>(optional)</td><td>Tomorrow will be even better</td></tr>
<tr><td>1234569</td><td>(optional)</td><td>December is the best month of the year!</td></tr>
</table>
For now, I'm using two separate preg_replacements, one for the first line (date) and a second one for the following ones, which can be just one or up to 100 or so. But, this file can contain other text as well, which needs to be ignored (as for the replacement), but if this line has more or less the same format (7 digits and some text) it gets formatted as well :
$file = preg_replace('~^\s*((\[.*\]){0,2}\d{1,2}:\d{2}:\d{2}(\[/.*\]){0,2})\s(\d{2}-\d{2}-\d{2}(\[/.*\]){0,2})\s+(?:\d{2}/\d{3}\s+|)(Monday|Tuesday|Wednesday|Thursday|Friday|Saturday|Sunday)\s+(.+)$~m', '<table class="file"><tr class="entry"><td class="time">$1 $4</td><td class="day">$6</td><td class="message">$7</td></tr>', $file);
$file = preg_replace('~^\s*(.{0,11}?)\s*((\[.+?\])?\d{7}(\[/.+?\])?)\s+(.+?)$~m', '<tr class="id"><td class="optional">$1</td><td class="id">$2</td><td class="message">$5</td></tr>', $file);
How to improve this? Like, if I have this content :
09:19:49 13-12-15 Sunday Hello World
1234567 Today is a beautiful day
1234568 Tomorrow will be even better
1234569 December is the best month of the year!
Liverpool - WBA 2-2
1234570 This line should be ignored
19:29:59 13-12-15 Sunday Hello World
1234571 Today is a beautiful day
1234572 Tomorrow will be even better
So, I'd like to catch and preg_replace only the first block and the last one, starting with time/date and some following lines, starting with a 7-digit ID.
So far, thanks for reading ;)
I think this accomplishes what you are trying to do.
There was one line that were unclear to me why it should be ignored:
1234570 This line should be ignored
This line meets the 7 digits and some text requirement.
The regex I came up with was:
/^(\d{2}:\d{2}:\d{2}\h*\d{1,2}-\d{1,2}-\d{1,2}|\d{7})\h*([a-zA-Z]{3}day)?\h*(.+)/m
Here is a regex101 demo: https://regex101.com/r/qB0gH6/1
and in PHP usage:
$string = '09:19:49 13-12-15 Sunday Hello World
1234567 Today is a beautiful day
1234568 Tomorrow will be even better
1234569 December is the best month of the year!
Liverpool - WBA 2-2
1234570 This line should be ignored
19:29:59 13-12-15 Sunday Hello World
1234571 Today is a beautiful day
1234572 Tomorrow will be even better';
echo preg_replace('/^(\d{2}:\d{2}:\d{2}\h*\d{1,2}-\d{1,2}-\d{1,2}|\d{7})\h*([a-zA-Z]{3}day)?\h*(.+)/m', '<td>$1</td><td>$2</td><td>$3</td>', $string);
Output:
<td>09:19:49 13-12-15</td><td>Sunday</td><td>Hello World</td>
<td>1234567</td><td></td><td>Today is a beautiful day</td>
<td>1234568</td><td></td><td>Tomorrow will be even better</td>
<td>1234569</td><td></td><td>December is the best month of the year!</td>
Liverpool - WBA 2-2
<td>1234570</td><td></td><td>This line should be ignored</td>
<td>19:29:59 13-12-15</td><td>Sunday</td><td>Hello World</td>
<td>1234571</td><td></td><td>Today is a beautiful day</td>
<td>1234572</td><td></td><td>Tomorrow will be even better</td>
Okay, per your update it is a bit more complicated but I think this does it:
$string = '09:19:49 13-12-15 Sunday Hello World
1234567 Today is a beautiful day
1234568 Tomorrow will be even better
1234569 December is the best month of the year!
Liverpool - WBA 2-2
1234570 This line should be ignored
19:29:59 13-12-15 Sunday Hello World
1234571 Today is a beautiful day
1234572 Tomorrow will be even better';
echo preg_replace_callback('/(?:^|\n)(\d{2}:\d{2}:\d{2}\h*\d{1,2}-\d{1,2}-\d{1,2})\h+([a-zA-Z]{3}day)?\h*(.+?)\n((\d{7})\h+(.+?)(\n|$))+/',
function ($matches) {
$lines = explode("\n", $matches[0]);
$theoutput = '<table><tr>';
foreach($lines as $line) {
if(preg_match('/(?:^|\n)(\d{2}:\d{2}:\d{2}\h*\d{1,2}-\d{1,2}-\d{1,2})\h+([a-zA-Z]{3}day)?\h*(.*)/', $line, $output)) {
//it is the first date string line;
foreach($output as $key => $values) {
if(!empty($key)) {
$theoutput .= '<td>' . $values . '</td>';
}
}
} else {
if(preg_match('/(\d{7})\h*(.*)/', $line, $output)) {
$theoutput .= '</tr><tr>';
foreach($output as $key => $values) {
if(!empty($key)) {
$theoutput .= '<td>' . $values . '</td>';
}
}
}
}
}
$theoutput .= '</tr></table>';
return $theoutput;
}, $string);
Output:
<table><tr><td>09:19:49 13-12-15</td><td>Sunday</td><td>Hello World</td></tr><tr><td>1234567</td><td>Today is a beautiful day</td></tr><tr><td>1234568</td><td>Tomorrow will be even better</td></tr><tr><td>1234569</td><td>December is the best month of the year!</td></tr></table>
Liverpool - WBA 2-2
1234570 This line should be ignored
<table><tr><td>19:29:59 13-12-15</td><td>Sunday</td><td>Hello World</td></tr><tr><td>1234571</td><td>Today is a beautiful day</td></tr><tr><td>1234572</td><td>Tomorrow will be even better</td></tr></table>

Simple regex trying to extract 3 or 4 numbers from "dirty" time string

Despite some help earlier on I am still floundering in regex problems and now in array problems.
I am trying to allow users to put time in as 205pm 1405 14:05 2.05 pm and so on.
Previously I had times stored as 14:05 (standard mySQL TIME format) but users were not liking that but if I convert to 2:05 pm then, when the updated values are entered (in similar format), that obviously breaks the database.
I have NO TROUBLE going 14:05 to 2:05 pm but I am having a nightmare going in the opposite direction.
I have fudged things a bit with a cascading IF statement to get the string length but I have spent literally hours trying to get at the output.
IE if I get 2-05 pm, to start off with I just want to get 205.
Here is my atrocious code:
if ($_POST['xxx']='yyy')
{
$stuff=$_POST['stuff'];
$regex='/^\d\D*\d\D*\d\D*\d\D*\d\D*$/';
if (preg_match($regex, $stuff, $matches)) {echo " More than 4 digits. This cannot be a time."; }
else{
$regex='/^\d\D*\d\D*\d\D*\d\D*$/';
if (preg_match($regex, $stuff, $matches)) {echo " >>4 digits";}
else{
$regex='/^\d\D*\d\D*\d\D*$/';
if (preg_match($regex, $stuff, $matches)) {echo " >>3 digits";}
else{
$regex='/^\d\D*\d\D*$/';
if (preg_match($regex, $stuff, $matches)) {echo " Less than 3 digits. This cannot be a time.";}
}
}
}
}
debug ($matches,"mat1");
$NEWmatches = implode($matches);
debug ($matches,"matN1");
preg_match_all('!\d+!', $NEWmatches, $matches);
debug ($matches,"mat2");
$matches = implode($matches);
debug ($matches,"mat3");
echo "<br> Matches $matches"; /// I hoped to get the digits only here
?>
Thanks for any help.
$times = array(
'205pm', '1405', '4:05', '2.05 pm'
);
foreach($times as $time)
{
// parsing string into array with 'h' - hour, 'm' - minutes and 'ap' keys
preg_match('/(?P<h>\d{1,2})\D?(?P<m>\d{2})\s*(?P<ap>(a|p)m)?/i', $time, $matches);
// construction below is not necessary, it just removes extra values from array
$matches = array_intersect_key($matches,
array_flip(array_filter(array_keys($matches), 'is_string')));
// output the result
var_dump($matches);
}
If you are using that string at strtotime then it is easier just to reformat it to the correct format, like this
$times = array(
'205pm', '1405', '4:05', '2.05 pm'
);
var_dump(preg_replace('/(\d{1,2})\D?(\d{2})(\s*(a|p)m)?/i', '$1:$2$3', $times));
ps: for more complex possible situations I would suggest to reformat the time and do something like this, otherwise regexp can be a nightmare..
$times = array(
'9 pm', '205pm', '1405', '4:05', '2.05 pm'
);
$times = preg_replace('/(\d{1,2})\D?(\d{2})(\s*(a|p)m)?/i', '$1:$2$3', $times);
foreach($times as $time)
{
$date = strtotime($time);
if ($date === false) { echo 'Unable to parse the time ' . $time . "\n"; continue; }
$hour = date('G', $date);
$minutes = date('i', $date);
echo $hour . " : " . $minutes . "\n";
}
For your given example "2-05 or 14:05" you can use this RegEx:
^(?<HOUR>[0-9]{1,2})\s{0,}((-|:|\.)\s{0,})?(?<MIN>[0-9]{2})\s{0,}(?<MODE>(a|p)m)?$
"Hour" will hold the the first 2 numbers of the string, "MIN" will always hold the last 2 numbers of the string. "MODE" will hold (am or pm)
So you can combine them at the end to an single string. Also you can just run an simple Replace("-","").

time period in time period (PHP)

i try to find out if a Timeperiod is inside a timeperiod. I have my reference time period and my comparative time period.
Let me make an example:
Time period A (reference) goes from 1.1.2014 to 1.2.2014 (tt.mm.yyyy).
Time period B (comparative) goes from 1.4.2014 to 1.5.2014.
=> This would be totaly ok.
Time period C (reference) goes from 1.1.2014 to 1.3.2014
Time period D (comparative) goes from 1.2.2014 to 1.5.2014.
=> Not ok because D is in C.
I hope you get what i want. I tried to make serval < = > if actions but this starts to get to huge and slow. Maybe there is a faster ways to do so.
Also, is MySQL able to do such things?
you can try this with php timestamp
$reference_start_date = "1.1.2014";
$reference_end_date = "1.2.2014";
$comparative_start_date = "1.4.2014";
$comparative_end_date = "1.5.2014 ";
$reference_start_time = strtotime(str_replace(".", "-", $reference_start_date);
$reference_end_time = strtotime(str_replace(".", "-", $reference_end_date);
$comparative_start_time = strtotime(str_replace(".", "-", $comparative_start_date);
$comparative_end_time = strtotime(str_replace(".", "-", $comparative_end_date);
if($comparative_start_time>$reference_start_time && $comparative_start_time<$reference_end_time)
{
echo "Not OK";
}
else if($comparative_end_time>$reference_start_time && $comparative_end_time<$reference_end_time)
{
echo "Not OK";
}
else if($comparative_start_time<$reference_start_time && $comparative_end_time>$reference_end_time)
{
echo "Not OK";
}
else
{
echo "OK";
}
you can do like below:
Check Reference_start >= comparative_start && Reference_end < comparative_end, If this condition become true than your time will be overlapped.
If you have a reference period (having startDate and endDate) and you have a comparative period, then you can have this where clause in MySQL:
where ((reference.startDate > comparative.endDate) or reference.endDate < comparative.startDate)
which would be true if the two periods have no intersection.
Assuming you have your dates give in UTC it is really simple to compare two date ranges. There are 5 specific cases that could happen:
11111......
......22222
..11111.....
.....22222..
...11111....
...22222....
.....11111..
..22222.....
......11111
22222......
Only the first and the last one are the ones you are looking for. It's easy to construct an if query of it and negate it:
if (!($dateRange1End <= $dateRangeStart2 && $dateRange2End <= $dateRange1Start))
// NOT OKAY
else
// OKAY

compare dates not working

Hallo,
I am comparing 2 dates. It is clear that $db_minus7 is greater so the value of $can_invoiced should be 'maybe' but it is 'Yes'. When i execute.
<?php
$db_minus7 = '2010-07-05 09:45:29.420';
$completion_date = '30.07.2009';
if(date("m-d-Y",strtotime($db_minus7)) > date("m-d-Y",strtotime($completion_date))) {
$can_invoiced = 'maybe';
} else {
$can_invoiced = 'Yes';
}
echo $can_invoiced;
?>
please help
why don't you just compare the times instad of formating them again like this:
if(strtotime($db_minus7) > strtotime($completion_date)) {
$can_invoiced = 'maybe';
} else {
$can_invoiced = 'Yes';
}
EDIT:
if you want to use date(), use "Ymd" or "Y-m-d" as pattern because it's string-comparision, and this is the logical order to work with (arrange the patterns from "big"(years) to small (days... or maybe seconds, if you need));
Dont' use "m-d-Y" but "Y-m-d".
01-01-2010 is lower than 02-01-2009 (bad !) but 2010-01-01 is not lower than 2009-01-02 (good !).
Compare the dates as datestamps, not as strings:
if(strtotime($db_minus7) > strtotime($completion_date)) {
If you have to compare the dates as strings, then use Y-m-d rather than m-d-y
Never Compare Dates as strings, even if it works for your Testcases it will fall on your feets sooner or later ... or maybe... richard stallman will hunt you down, i don't know ...
if(strtotime($db_minus7) > strtotime($completion_date)) {
$can_invoiced = 'maybe';
} else {
$can_invoiced = 'Yes';
}

Categories