1

I am trying to sort an array without it being alphabetical. In my case I want the order of the messages returned to be error, warning and then info. Reading about this at W3 I found a similar example...

They give this example with cars but have changed it too messages for my use case.

var message = [
  {type:"Error", message:"This is an Error"},
  {type:"Info", message:"This is an Info"},
  {type:"Warning" message:"This is a Warning"}
];


function myFunction() {
  message.sort(function(a, b){
    var x = a.type.toLowerCase();
    var y = b.type.toLowerCase();
    if (x < y) {return -1;}
    if (x > y) {return 1;}
    return 0;
  });
}

I thought this was all about scoring the value so I thought this might be right way to do it but it isnt giving me the expected results...

function myFunction() {
  message.sort(function(a, b){
    var x = a.type.toLowerCase();
    var y = b.type.toLowerCase();
    if (x === 'error') {return 1;}
    if (x === 'warning') {return 2;}
    if (x === 'info') {return 3;}
    return 0;
  });
}
2

3 Answers 3

1

You can compare y after each time you compare x:

var message = [
  {type:"Error", message:"This is an Error"},
  {type:"Info", message:"This is an Info"},
  {type:"Warning", message:"This is a Warning"}
];


function myFunction() {
  message.sort(function(a, b){
     var x = a.type.toLowerCase();
     var y = b.type.toLowerCase();
     if (x === 'error') {return -1;}
     else if(y === 'error'){return 1;}
     else if (x === 'warning') {return -1;}
     else if (y === 'warning') {return 1;}
     else if (x === 'info') {return -1;}
     else if (y === 'info') {return 1;}
     return 0;
  });
}

myFunction();
console.log(message);

Sign up to request clarification or add additional context in comments.

1 Comment

Thank you very much, I wasn't sure the purpose of x vs y but seeing how you wrote that totally makes sense now. Thank you very much!
0

You could take an object with the wanted order and return the delta of the wanted order in the sorting callback.

For sorting unknown types to the end of the array use a large value.

const 
    order = { error: 1, warning: 2, info: 3, default: Number.MAX_VALUE },
    message = [{ type: '' }, { type: "Error", message: "This is an Error" }, { type: "Info", message: "This is an Info" }, { type: "Warning", message: "This is a Warning" }, { type: '' }];

message.sort(({ type: a }, { type: b }) =>
    (order[a.toLowerCase()] || order.default) - (order[b.toLowerCase()] || order.default)
);

console.log(message);
.as-console-wrapper { max-height: 100% !important; top: 0; }

1 Comment

That looks like another great way to accomplish it thanks for sharing!
0

You should have weights for all your log messages for filtering (and sorting, if that's what you need).

I adopted Java's java.util.logging.Level class to introduced various weights for log messages; depending on their severity.

/**
 * Based on:
 * https://docs.oracle.com/javase/8/docs/api/java/util/logging/Level.html
 */
const LogLevel = {
  OFF     : { value: Number.MAX_VALUE }, 
  ERROR   : { value: 1000             }, // Based on Level.SEVERE
  WARNING : { value: 900              },
  INFO    : { value: 800              },
  DEBUG   : { value: 500              }, // Based on Level.FINE
  ALL     : { value: Number.MIN_VALUE }
};

class LogUtils {
  static sortMesages(messages) {
    return messages.sort(({ type: a }, { type: b }) => {
      if (b == null || LogLevel[b.toUpperCase()] == null) return -1;
      if (a == null || LogLevel[a.toUpperCase()] == null) return 1;
      return LogLevel[b.toUpperCase()].value -
             LogLevel[a.toUpperCase()].value;
    });
  }
}

const logMessages = [
  { type: "Error",   message: "This is an Error"  },
  { type: "Info",    message: "This is an Info"   },
  { type: "Warning", message: "This is a Warning" }
];

console.log(LogUtils.sortMesages(logMessages));
.as-console-wrapper { top: 0; max-height: 100% !important; }

Here are some other implementations of logging weights in third-party JS libraries:

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.