I would like you to help me with an algorithm in PHP that can loop through an array of values, sort them and print non-duplicates.
Here is the code I wrote. I want to do it with only loop and if else statement. I would appreciate any help in achieving this. Thanks
$input_array = [3, 5, 7, 7, 8, 3, 1, 9, 9, 9, 0, 2, 4, 8, 0, 12, 5, 8, 2];`
$count_array = count($input_array); // count the array`enter code here`
for($i = 0; $i < $count_array; $i++){ //loop through the array 1st time
$check_array = false;
//sort array
for($j = $i+1; $j < $count_array; $j++){
if($input_array[$i] > $input_array[$j]){
$non_duplicates = $input_array[$i];
$input_array[$i] = $input_array[$j];
$input_array[$j] = $non_duplicates;
}
else if($input_array[$i] == $input_array[$j] &&( $i != $j)){
$check_array = true;
break;
}
else{
$input_array[$i] != $input_array[$j];
}
}
if(!$check_array){
echo($input_array[$i]. ', ');
}
}
You can do it with 2 for cycles where the first cycle is for the first element and the 2nd cycle is always in the next position, this will help to always check if the first number is less than the second. You create a temporary variable where you store the value of the first number and you pass the value of the second number to the variable of the first one, later the temporary one that you had stored you pass it to the variable of the second number (with this you got to invert the values of one to the other).
As this is ordering them, later an if is made where it is verified if they are equal, in case of being equal a unset() is made to eliminate that data of the array.
// Array of values
$input_array = [3, 5, 7, 7, 8, 3, 1, 9, 9, 9, 0, 2, 4, 8, 0, 12, 5, 8, 2];
// count the length of array
$count = count($input_array);
// order array and remove duplicates
for ($i = 0; $i < $count; $i++) {
for ($j = $i + 1; $j < $count; $j++) {
// order array
if ($input_array[$i] < $input_array[$j]) {
$temp = $input_array[$i];
$input_array[$i] = $input_array[$j];
$input_array[$j] = $temp;
}
// delete duplicates
if ($input_array[$i] == $input_array[$j]) {
unset($input_array[$j]);
}
}
}
// Return an array with elements in reverse order
$input_array = array_reverse($input_array);
You get something like this:
Dump => array(9) {
[0] => int(1)
[1] => int(2)
[2] => int(3)
[3] => int(4)
[4] => int(7)
[5] => int(5)
[6] => int(8)
[7] => int(9)
[8] => int(12)
}
Related
I have two different arrays like this
$array1 = [1, 2, 8, 10];
$array2 = [2, 4, 6, 8, 10, 15, 1];
I want to get the common elements and uncommon elements between them.
I almost figured out how to get the common ones as the code below but I can't get uncommon elements.
for($x = 0; $x < count($array1); $x++) {
for($z = 0; $z < count($array2); $z++) {
if ( $array1[$x] == $array2[$z] ) {
$array3 = $array1[$x];
print_r($array3);
} elseif ($array1[$x] !== $array2[$z]) {
// code...
}
}
}
How to get those uncommon or different elements between the two arrays without using a built-in PHP method then output them in a new array.
You can get the uncommon elements by using in_array() function
<?php
$array1 = [1, 2, 8, 10];
$array2 = [2, 4, 6, 8, 10, 15, 1];
$result = [];
for($i = 0;$i < sizeof($array2);$i++){
if(!in_array($array2[$i],$array1)){
$result[] = $array2[$i];
}
}
?>
Output
Array
(
[0] => 4
[1] => 6
[2] => 15
)
Here is my array
$array = array( 0 => 10, 1 => 9, 2 => 8, 3 => 6, 4=> 4 );
I want to get array value 6. because, 7 is missing before this value/series is break.
Please help me how can I do it easy & fast method.
The sequence could be calculated by subtracting the first value from the second value. Then you could for example use a for loop to loop through the values of the array and check if there is also a next value available by checking if there is an index + 1.
Then if that is the case you can subtract the current value in the loop from the next value and check if that result equals the step size.
If that is not the case, the next value of the iteration is the value that breaks the sequence and you can break out of the loop.
$array = [10,9,8,6,4];
if (count($array) > 2) {
$step = $array[0] - $array[1];
for ($i = 0; $i < count($array); $i++) {
if (isset($array[$i + 1]) && $array[$i] - $array[$i + 1] !== $step) {
$wrongValue = $array[$i + 1];
echo sprintf(" The step count is %d, but after %d comes %d which breaks the sequence.",
$step, $array[$i], $wrongValue
);
break;
}
}
}
Demo
<?php
$sequence =
[
0 => 10,
1 => 9,
3 => 8,
4 => 6,
5 => 4
];
$last = null;
foreach($sequence as $k => $v)
{
if(!is_null($last) && $last - $v > 1)
break;
$last = $v;
}
var_dump($k, $v);
Output:
int(4)
int(6)
Loop through it, save the previous values and compare with current one:
<?php
function findMissing($array) {
$missing = [];
foreach($array as $key => $val) {
if(isset($previousValue) && $previousValue-1!=$val) {
echo "not in series: ".($previousValue-1) .", returning ".$val."<br>\n";
$missing[] = $val;
}
$previousValue=$val;
}
return $missing;
}
// USAGE:
$array = array( 0 => 10, 1 => 9, 2 => 8, 3 => 6, 4=> 4 );
findMissing($array);
// not in series: 7, returning 6
// not in series: 5, returning 4
$array2 = array( 10, 9, 8, 6, 5 );
$missingValues = findMissing($array2);
// not in series: 7, returning 6
var_dump($missingValues);
// array(1) { [0]=> int(6) }
I'm not sure I understand what you want to achieve, but let's start it here.
UPDATED:
for($i = 0; $i < count($array); ++$i) {
if($i > 0) {
if($array[$i] != ($array[$i-1]-1)) {
echo($array[$i]);
break;
}
}
}
Output:
6
I am trying to compute the difference between all values in an array and store them (the differences) in a single array.
An ideal example would be something like this:
<?php
$data = array('1', '5', '12');
// Compute the difference between each value with another value.
?>
And then I like to have the following results in an array:
4, 11, 7
How can I achieve it?
try this
$data = array('1', '5', '12');
$differences=[];
for($i=0;$i<count($data);$i++){
for($j=$i+1;$j<count($data);$j++){
$differences[]=abs($data[$i]-$data[$j]);
}
}
print_r($differences);
results in
Array
(
[0] => 4
[1] => 11
[2] => 7
)
Try by having double for loops one for iterating current array and another to start comparing and store it in result array.
I am not very sure about your output as information is less but you can try as follow:
var a= ["1","5","12"]
for(i=0;i<3;i++){for(j=0;j<3;j++){if(i>j)console.log(a[i]-a[j])}}
Check this https://3v4l.org/9oiqs
$data = [1, 5, 12, 15, 20, 25,];
function getDifferences($aValues)
{
$aDiff = [];
$iSize = count($aValues);
for ($i = 0; $i < $iSize; $i++)
{
for ($j = $i + 1; $j < $iSize; $j++)
{
$aDiff[$aValues[$i]][] = abs($aValues[$i] - $aValues[$j]);
}
}
return $aDiff;
}
function printDifferences($aValues){
foreach ($aValues as $iNumber => $aDiffs){
echo "Differences for $iNumber: " . implode(', ', $aDiffs) . PHP_EOL;
}
}
$aDiff = getDifferences($data);
printDifferences($aDiff);
Result
Differences for 1: 4, 11, 14, 19, 24
Differences for 5: 7, 10, 15, 20
Differences for 12: 3, 8, 13
Differences for 15: 5, 10
Differences for 20: 5
$teams = array(1, 2, 3, 4, 5, 6, 7, 8);
$game1 = array(2, 4, 6, 8);
$game2 = array();
if teams[x] is not in game1 then insert into game2
for($i = 0; $i < count($teams); $i++){
for($j = 0; $j < count($game1); $j++){
if($teams[$i] == $game1[$j]){
break;
} else {
array_push($game2, $teams[$i]);
}
}
}
for ($i = 0; $i < count($game2); $i++) {
echo $game2[$i];
echo ", ";
}
Im expecting the result to be:
1, 3, 5, 7,
However, im getting:
1, 1, 1, 1, 3, 3, 3, 3, 4, 5, 5, 5, 5, 6, 6, 7, 7, 7, 7, 8, 8, 8,
How can i improve this? Thanks
Others have already answered on how to use array_diff.
Reason why your existing loop does not work:
if($teams[$i] == $game1[$j]){
// this is correct, if item is found..you don't add.
break;
} else {
// this is incorrect!! we cannot say at this point that its not present.
// even if it's not present you need to add it just once. But now you are
// adding once for every test.
array_push($game2, $teams[$i]);
}
You can use a flag to fix your existing code as:
for($i = 0; $i < count($teams); $i++){
$found = false; // assume its not present.
for($j = 0; $j < count($game1); $j++){
if($teams[$i] == $game1[$j]){
$found = true; // if present, set the flag and break.
break;
}
}
if(!$found) { // if flag is not set...add.
array_push($game2, $teams[$i]);
}
}
Your loop doesn't work because every time the element from $teams is not equal to the element from $game1, it adds the $teams element to $game2. That means each element is being added to $game2 multiple times.
Use array_diff instead:
// Find elements from 'teams' that are not present in 'game1'
$game2 = array_diff($teams, $game1);
You can use PHP's array_diff():
$teams = array(1, 2, 3, 4, 5, 6, 7, 8);
$game1 = array(2, 4, 6, 8);
$game2 = array_diff($teams,$game1);
// $game2:
Array
(
[0] => 1
[2] => 3
[4] => 5
[6] => 7
)
I have an array in the following format:
array(
0 => array(1, 5),
1 => array(4, 8),
2 => array(19, 24),
3 => array(6, 9),
4 => array(11, 17),
);
Where each item is a X-to-Y range. What I would like to merge the overlapping ranges in the array, to get something more like this:
array(
0 => array(1, 9), // 1-5, 4-8 and 6-9 are overlapping, so they are merged
1 => array(11, 17),
2 => array(19, 24),
);
What would be the best way to accomplish this?
Untested, but the idea here is to sort the data first by the first element, then merge subsequent elements with the previous one as long as possible.
usort($data, function($a, $b)
{
return $a[0] - $b[0];
});
$n = 0; $len = count($data);
for ($i = 1; $i < $len; ++$i)
{
if ($data[$i][0] > $data[$n][1] + 1)
$n = $i;
else
{
if ($data[$n][1] < $data[$i][1])
$data[$n][1] = $data[$i][1];
unset($data[$i]);
}
}
$data = array_values($data);
$input = array( 0 => array(1, 5),
1 => array(4, 8),
2 => array(19, 24),
3 => array(6, 9),
4 => array(11, 17),
);
$tmpArray = array();
foreach($input as $rangeSet) {
$tmpArray = array_unique(array_merge($tmpArray,range($rangeSet[0],$rangeSet[1])));
}
sort($tmpArray);
$oldElement = array_shift($tmpArray);
$newArray = array(array($oldElement));
$ni = 0;
foreach($tmpArray as $newElement) {
if ($newElement > $oldElement+1) {
$newArray[$ni++][] = $oldElement;
$newArray[$ni][] = $newElement;
}
$oldElement = $newElement;
}
$newArray[$ni++][] = $oldElement;
var_dump($newArray);
Alright, drafted this up, so it may have quirks. Tested it with the data seen below and seemed to work just fine. May not be the best way to do it, but it is one way and it does work. Questions let me know.
function combineRange($array) {
if (is_array($array)) {
// Sort the array for numerical order
sort($array);
// Set Defaults
$prev = array();
$prev_key = null;
foreach ($array as $key => $item) {
// First time around setup default data
if (empty($prev)) {
$prev = $item;
$prev_key = $key;
continue;
}
if ($item[0] >= $prev[0] && $item[0] <= $prev[1]) {
// Incase the last number was less than do not update
if ($array[$prev_key][1] < $item[1])
$array[$prev_key][1] = $item[1];
unset($array[$key]);
}else {
$prev_key = $key;
}
$prev = $item;
}
}
return $array;
}
$array = array(
5 => array(13, 16),
0 => array(1, 5),
1 => array(4, 8),
2 => array(19, 24),
3 => array(6, 9),
4 => array(11, 17),
6 => array(21, 30),
);
var_dump(combineRange($array));
Outputs:
array(3) {
[0]=>
array(2) {
[0]=>
int(1)
[1]=>
int(9)
}
[3]=>
array(2) {
[0]=>
int(11)
[1]=>
int(17)
}
[5]=>
array(2) {
[0]=>
int(19)
[1]=>
int(30)
}
}
Hope it works for ya!
EDIT
I see I was beaten out by an hour =\ Oh well! I am still posting as it is a different method, granted I would probably choose konforce's method instead.