3

I have a function where I get the first non empty value in a multidimensionnal array. In my example the first non empty value is B because I through the array by thecolumns first. Now, in this function, I need to get also the last non empty value. In my example "C" is the last non empty value. Because "C" is in the furthest column. So... How I can get C in my function ?

Thank you !

function findFirstAndLastValue (timeline) {
  for (var col = 0; col < timeline[0].length; col++) {
      for (var row = 0; row < 4; row++) {
        if (timeline[row][col] != '') {
          return [row, col];
        }
      }
    }
}

function getFirstAndLastValue() {
    var projectTl = [
      ['','','A','A','',''],
      ['','B','B','','',''],
      ['','','','','C',''],
      ['','','D','D','','']
    ] 

    var position = findFirstAndLastValue(projectTl);
    console.log(position)
}

getFirstAndLastValue();
christophebazin
  • 200
  • 2
  • 4
  • 14

4 Answers4

2

Using your exact same code, but making it loop backwards instead of forwards gets you the desired result.. you could also reverse the array, or take any number of "functional" approaches.

function findFirstAndLastValue (timeline) {
  for (var col = timeline[0].length; col--;) {
      for (var row = 4; row--;) {
        if (timeline[row][col] != '') {
          return [row, col];
        }
      }
    }
}

var projectTl = [
  ['','','A','A','',''],
  ['','B','B','','',''],
  ['','','','','C',''],
  ['','','D','D','','']
] 

  var position = findFirstAndLastValue(projectTl);
  console.log(position)
I wrestled a bear once.
  • 22,983
  • 19
  • 69
  • 116
2

You could use reduce() method and return one object as a result.

var projectTl = [
  ['', '', 'A', 'A', '', ''],
  ['', 'B', 'B', '', '', ''],
  ['', '', '', '', 'C', ''],
  ['', '', 'D', 'D', '', '']
]

const findInArr = data => {
  let temp = {
    first: null,
    last: null
  }
  return data.reduce((r, arr) => {
    arr.forEach(function(e, i) {
      if (e) {
        if (temp.last == null || i > temp.last) {
          temp.last = i
          r.last = e
        }
        if (temp.first == null || i < temp.first) {
          temp.first = i;
          r.first = e;
        }
      }
    })
    return r;
  }, Object.assign({}, temp))
}

console.log(findInArr(projectTl))
Nenad Vracar
  • 118,580
  • 15
  • 151
  • 176
  • Why this `Object.assign({}, temp)` and not only `temp`? Why create a new object for the `initialValue`? Curiosity :-) – Ele Feb 02 '18 at 18:17
  • One is for index other one for values, also they are passed by reference so we need to create shallow copy. – Nenad Vracar Feb 02 '18 at 18:18
  • I know that, my concern is about the creation of a new object calling `Object.assign({}, temp)` rather than just passing `temp` as an `initialValue`. – Ele Feb 02 '18 at 18:19
2

If you are looking for one liner in js, you can do it like this

// For Single arrays | get last non empty value 
let your_array = ['','A','B','','C','', ''];
let last_non_empty_value = your_array.filter(item => item).pop(-1);
console.log(last_non_empty_value);

// for Getting Last Non Empty values only from multi-dimensional arrays
let a = [
    ['', '', 'A', 'E', '', ''],
    ['', 'B', 'C', '', '', ''],
    ['', '', '', '', 'D', ''],
    ['', '', 'F', 'G', '', '']
];
let last_values = a.map(item=>item.filter(item=>item).pop());
console.log(last_values);
ksodari
  • 67
  • 8
0

You need to loop your cols from the last index:

for (var col = timeline[0].length - 1; col > 0; col--)

function findFirstAndLastValue(timeline) {
 var result = {
 "first": [],
 "last": []
 };
  first: for (var col = 0; col < timeline[0].length; col++) {
    for (var row = 0; row < 4; row++) {
      if (timeline[row][col] != '') {
         result.first = [row, col];
         break first;
      }
    }
  }
  
  last: for (var col = timeline[0].length - 1; col > 0; col--) {
    for (var row = 0; row < 4; row++) {
      if (timeline[row][col] != '') {
        result.last = [row, col];
        break last;
      }
    }
  }
  
  return result;
}

function getFirstAndLastValue() {

  var projectTl = [
    ['', '', 'A', 'A', '', ''],
    ['', 'B', 'B', '', '', ''],
    ['', '', '', '', 'C', ''],
    ['', '', 'D', 'D', '', '']
  ]

  var position = findFirstAndLastValue(projectTl);
  console.log(position);
}

getFirstAndLastValue();
Ele
  • 33,468
  • 7
  • 37
  • 75