A less imperative code

In the sample code below, it basically re-arranges the order of an array by using the slice method. I’ve chosen the slice method because it’s a non-destructive one. The conventional for loop I wish I could use a foreach (doable), but it would be nice to have a way to offset it otherwise I’ll be imperative again buy using if(idx === 0) do something. Maybe there’s a way to be more functional? Plus there’s usage of let vars

const major = {
   base: ["C", "D", "E", "F", "G", "A", "B"],
   flats: [[], [], [], [], [], [], []],
   createCircleOf4ths: function () {
      let left = this.base.slice(0, 3);
      let right = this.base.slice(3);
      this.flats[0] = right.concat(left);
      this.flats[0][3] = this.flats[0][3] + "b";
      for (let i = 1; i < 7; i++) {
         left = this.flats[i - 1].slice(0, 3);
         right = this.flats[i - 1].slice(3);
         this.flats[i] = right.concat(left);
         this.flats[i][3] = this.flats[i][3] + "b";
      }
   },
};

The output would be:

0: (7) ["F", "G", "A", "Bb", "C", "D", "E"]
1: (7) ["Bb", "C", "D", "Eb", "F", "G", "A"]
2: (7) ["Eb", "F", "G", "Ab", "Bb", "C", "D"]
3: (7) ["Ab", "Bb", "C", "Db", "Eb", "F", "G"]
4: (7) ["Db", "Eb", "F", "Gb", "Ab", "Bb", "C"]
5: (7) ["Gb", "Ab", "Bb", "Cb", "Db", "Eb", "F"]
6: (7) ["Cb", "Db", "Eb", "Fb", "Gb", "Ab", "Bb"]

All the useful major scales with flat accidentals.

As first attempt, I’ve used a major scale filter, and a separate map that walks up the scale by fourths.

const notes = ["C", "Db", "D", "Eb", "E", "F", "Gb", "G", "Ab", "A", "Bb", "B"];
function majorFilter(note, index) {
    return [0, 2, 4, 5, 7, 9, 11].includes(index);
}
const circleOfFourths = notes.map(function (note, index) {
    const start = index * 5 % notes.length;
    const scale = notes.concat(notes).slice(start, start + 12);
    return scale.filter(majorFilter);
});

Which gives:

  1. C,D,E,F,G,A,B
  2. F,G,A,Bb,C,D,E
  3. Bb,C,D,Eb,F,G,A
  4. Eb,F,G,Ab,Bb,C,D
  5. Ab,Bb,C,Db,Eb,F,G
  6. Db,Eb,F,Gb,Ab,Bb,C
  7. Gb,Ab,Bb,B,Db,Eb,F
  8. B,Db,Eb,E,Gb,Ab,Bb
  9. E,Gb,Ab,A,B,Db,Eb
  10. A,B,Db,D,E,Gb,Ab
  11. D,E,Gb,G,A,B,Db
  12. G,A,B,C,D,E,Gb

You can explore it at https://jsfiddle.net/pmw57/phr1o5ed/2/.

I’m not clued up on musical scales, so I will presume Paul’s is more accurate.

As an exercise though, for what it’s worth, to match Kodertian’s output

let base = ["C", "D", "E", "F", "G", "A", "B"]
let scales = [];

base.forEach(function(val, i, base){

    let from  = scales[i-1] || base

    scales[i] = from.slice(3).concat(from.slice(0, 3))
    scales[i][3] += 'b'
})

or

let scales = base.reduce((acc, curr, i, base) => {

    let from  = acc[i-1] || base

    acc[i] = from.slice(3).concat(from.slice(0, 3))
    acc[i][3] += 'b'

    return acc
}, [])

Output:

0: (7) ["F", "G", "A", "Bb", "C", "D", "E"]
1: (7) ["Bb", "C", "D", "Eb", "F", "G", "A"]
2: (7) ["Eb", "F", "G", "Ab", "Bb", "C", "D"]
3: (7) ["Ab", "Bb", "C", "Db", "Eb", "F", "G"]
4: (7) ["Db", "Eb", "F", "Gb", "Ab", "Bb", "C"]
5: (7) ["Gb", "Ab", "Bb", "Cb", "Db", "Eb", "F"]
6: (7) ["Cb", "Db", "Eb", "Fb", "Gb", "Ab", "Bb"]
2 Likes

This topic was automatically closed 91 days after the last reply. New replies are no longer allowed.