How do I return all possible combinations [12345], [12354] up to [54312], [54321] without having to run 120 for...loop as in the case of combining a 2-item array in the code below?
To return all possible combinations from the given array $word = [1,2],
//break the array into 2 separate arrays
$arr1 = $word[0]; $arr2 = $word[1];
//computer for first array item...each item will have 2 loops
for($i=0; $i<count($arr1); $i++){
for($j=0; $j<count($arr2); $j++){
$ret = $arr1[$i] . $arr2[$j]; array_push($result, $ret);
}
}
//computer for second array item..each item will have 2 loops
for($i=0; $i<count($arr2); $i++){
for($j=0; $j<count($arr1); $j++){
$ret = $arr2[$i] . $arr1[$j]; array_push($result, $ret);
}
}
//display the result
for ($i = 0; $i < count($result); $i++){
echo result([$i];
}
The above code works well.
But for a 5-item array [1,2,3,4,5], it will require about (5 items * 24 loops) = 120 loops.
As seen, you wanted to split 2 strings into chars and obtain all combination by 2 chars: first form blank1 and second from blank2.
Instead of doing the combination manually use a regular for-loop.
$result = array();
for ($i = 0; $i < count($blank1); $i++)
{
for ($j = 0; $j < count($blank2); $j++)
{
//set combination
$aux = $blank1[$i].$blank2[$j];
array_push($result, $aux);
}
}
//result should be populated with combination of 2
//just list it and use as need
for ($i = 0; $i < count($result); $i++)
{
echo $result[$i];
}
//same with stored or checking on db : use loops
For multiple combination, use more nested loops
eg: [blank1][blank2][blank1] - 3 combination
$result = array();
//1
for ($i = 0; $i < count($blank1); $i++)
{
//2
for ($j = 0; $j < count($blank2); $j++)
{
//3
for ($k = 0; $k < count($blank1); $k++)
{
//set combination
$aux = $blank1[$i].$blank2[$j].$blank1[$k];
array_push($result, $aux);
}
}
}
Same as any number you wanted ! It will be a little annoying if have to write many loops but note while can be used with an adequate algorithm. But for the moment just keep as simple as you can and get the desired result.
I have a BINARY(40) column in a MySQL and there I store 5 8 byte integers. I am trying to read those numbers in PHP one by one:
$result = mysqli_query($con,"SELECT data FROM list WHERE id=".$id);
$mysql_array = mysqli_fetch_array($result);
$list = str_split($mysql_array["data"], 8);
for($i = 0; $i < 5; $i++)
echo $list[$i]."<br/>";
Instead of the numbers I expect, weird symbols are printed. How can I convert those numbers from binary strings to integers?
Change your query as follows:
$result = mysqli_query($con,"SELECT cast(data as char(40)) FROM list WHERE id=".$id);
OK, because of the way you're storing the numbers, this code will only work if you've got 64 bit support, otherwise you'll have to look at a bc replacement, shouldn't be too difficult:
for($i = 0; $i < 5; $i++) {
$bin_str = $list[$i];
$int_val = 0;
for ($j = 0; $j < 8; ++$j) {
$byte_val = ord(substr($bin_str, $j, 1));
// push the next byte onto our integer:
$int_val = ($int_val << 8) + $byte_val;
}
echo $int_val;
}
EDIT: In all likelyhood this is a BC equiv, I'm unable to test it at the moment though, however the logic remains unchanged.
for($i = 0; $i < 5; $i++) {
$bin_str = $list[$i];
$bc_val = '0';
for ($j = 0; $j < 8; ++$j) {
$byte_val = ord(substr($bin_str, $j, 1));
// push the next byte onto our integer:
$bc_val = bcadd(bcmul($bc_val, 256, 0), "$byte_val", 0);
}
echo $bc_val;
}
I'm trying to align strings in PHP using Levenshtein distance algorithm. The problem is that my back tracing code does not work properly for all cases. For example when the second array has inserted lines at the beginning. Then the back tracing will only go as far as when i=0.
How to properly implement back tracing for Levenshtein distance?
Levenshtein distance, $s and $t are arrays of strings (rows)
function match_rows($s, $t)
{
$m = count($s);
$n = count($t);
for($i = 0; $i <= $m; $i++) $d[$i][0] = $i;
for($j = 0; $j <= $n; $j++) $d[0][$j] = $j;
for($i = 1; $i <= $m; $i++)
{
for($j = 1; $j <= $n; $j++)
{
if($s[$i-1] == $t[$j-1])
{
$d[$i][$j] = $d[$i-1][$j-1];
}
else
{
$d[$i][$j] = min($d[$i-1][$j], $d[$i][$j-1], $d[$i-1][$j-1]) + 1;
}
}
}
// backtrace
$i = $m;
$j = $n;
while($i > 0 && $j > 0)
{
$min = min($d[$i-1][$j], $d[$i][$j-1], $d[$i-1][$j-1]);
switch($min)
{
// equal or substitution
case($d[$i-1][$j-1]):
if($d[$i][$j] != $d[$i-1][$j-1])
{
// substitution
$sub['i'][] = $i;
$sub['j'][] = $j;
}
$i = $i - 1;
$j = $j - 1;
break;
// insertion
case($d[$i][$j-1]):
$ins[] = $j;
$j = $j - 1;
break;
// deletion
case($d[$i-1][$j]):
$del[] = $i;
$i = $i - 1;
break;
}
}
This is not to be nit-picky, but to help you find the answers you want (and improve your implementation).
The algorithm you are using is the Wagner-Fischer algorithm, not the Levenshtein algorithm. Also, Levenshtein distance is not use to align strings. It is strictly a distance measurement.
There are two types of alignment: global and local. Global alignment is used to minimize the distance between two entire strings. Example: global align "RACE" on "REACH", you get "RxACx". The x's are gaps.
In general, this is the Needleman-Wunsch algorithm, which is very similar to the Wagner-Fischer algorithm. Local alignment finds a substring in a long string and minimizes the difference between a short string and a the substring of the long string.
Example: local align "BELL" on "UMBRELLA" and you get "BxELL" aligned on "BRELL". It is the Smith-Waterman algorithm which, again, is very similar to the Wagner-Fischer algorithm.
I hope that this is helpful in allowing you to better define the exact kind of alignment you want.
I think your bug is exactly what you say in your question that it is: you stop as soon as i==0, instead of going all the way to i==0 && j==0. Simply replace this condition:
while($i > 0 && $j > 0)
with
while ($i > 0 || $j > 0)
and you're halfway to your solution. The tricky bit is that if $i==0, then it's incorrect to use the array index $i-1 in the loop body. So you'll also have to change the body of the loop to something more like
while ($i || $j) {
$min = $d[$i][$j]; // or INT_MAX or something
if ($i && $j && $min > $d[$i-1][$j-1]) {
$newi = $i-1;
$newj = $j-1;
$min = $d[$newi][$newj];
}
if ($i && $min > $d[$i-1][$j]) {
$newi = $i-1;
$newj = $j;
$min = $d[$newi][$newj];
}
if ($j && $min > $d[$i][$j-1]) {
$newi = $i;
$newj = $j-1;
$min = $d[$newi][$newj];
}
// What sort of transformation is this?
if ($newi == $i && $newj == $j) {
assert(false); // should never happen
} else if ($newi == $i) {
// insertion
$ins[] = $j;
} else if ($newj == $j) {
// deletion
$del[] = $i;
} else if ($d[$i][$j] != $d[$newi][$newj]) {
// substitution
$sub['i'][] = $i;
$sub['j'][] = $j;
} else {
// identity
}
assert($newi >= 0); assert($newj >= 0);
$i = $newi;
$j = $newj;
}
In php is there a function to increment the
values of subsequent values twice(*2) in an array
column based on an initial value?
$beta = array(
array('5', '1''1','1','1','1','1','1','1','1','1','1','1','1','1','1','1','1','1','1'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2'),
array('5','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2','2')
);
/*Example: '5' will be '10' (5*2 =10 and output 10 to web)
'2' will be '4' (2*2 = 4 and output 4 to web)
The next '2' will be '16' (4*2 = 8 and output 8 to web)
The next '2' will be '32' (8*2 = 16 and output 16 to web)
And so forth? */
Furthermore is there an easier way to construct this array, cause I firmly believe there is, but not something too complicated in terms of construct such that a noob will not understand it, again thanks.
[Disclaimer: I have spent 3 days trying to understand arrays, I now understand them; however, I am still new and am currently having some issues when trying to manipulate the values in my array and output them to the web.And I am still pretty sure I have a lot to read and learn, so please no flamers, I just need some help, found this problem in this C++ book:
[http://books.google.com/books?id=4Fn_P7tdOZgC&pg=PT424&lpg=PT424&dq=subsequent+++column+is+twice+the+value&source=bl&ots=gSvQ_LhxoI&sig=dG_Ilf1iLO86lqX936cT1PpkPc8&hl=en&ei=OEEBS_eODYyotgOFtJD3CQ&sa=X&oi=book_result&ct=result&resnum=1&ved=0CAgQ6AEwAA#v=onepage&q=subsequent%20%20%20column%20is%20twice%20the%20value&f=false][1]
You can try array_map:
<?php
function increase($n) {
return is_array($n) ? array_map('increase', $n) : $n * 2;
}
$new_beta = array_map("increase", $beta);
As for constructing the array, there are other methods to do so but I believe this is the most performent and clean.
Here is an answer for each question in that section of the book, enjoy!
<?php
// Declare an array alpha of 10 rows and 20 columns of type int
// Initialise the array alpha to 0
$alpha = array(array());
for($i = 0; $i < 10; $i++)
{
for($j = 0; $j < 20; $j++)
{
$alpha[$i][$j] = 0;
}
}
// Store 1 in the first row and 2 in the remaining rows
for($i = 0; $i < 10; $i++)
{
for($j = 0; $j < 20; $j++)
{
if($i == 0)
{
$alpha[$i][$j] = 1;
}
else
{
$alpha[$i][$j] = 2;
}
}
}
// Store 5 in the first column, and make sure that the value in
// each subsequent column is twice the value in the previous column
// (Beware this doesn't build off the initial value of 5 in the first
// column but the previously set values above)
for($i = 0; $i < 10; $i++)
{
for($j = 0; $j < 20; $j++)
{
if($j == 0)
{
$alpha[$i][$j] = 5;
}
else
{
if($j - 1 >= 1)
{
$alpha[$i][$j] = $alpha[$i][$j-1] * 2;
}
}
}
}
// Print the array alpha one row per line
print "Printing the array alpha one row per line:<br/>";
for($i = 0; $i < 10; $i++)
{
for($j = 0; $j < 20; $j++)
{
print "[". $alpha[$i][$j] ."] ";
}
print "<br/>";
}
print "<br/>";
// Print the array alpha one column per line
print "Printing the array alpha one column per line:<br/>";
for($j = 0; $j < 20; $j++)
{
for($i = 0; $i < 10; $i++)
{
print "[". $alpha[$i][$j] ."] ";
}
print "<br/>";
}
?>