преобразование массива байтов в 320 бит, а затем извлечение битов 16 бит, затем 10 бит

#javascript #arrays

#javascript #массивы

Вопрос:

я надеюсь, что некоторые умные люди здесь смогут мне помочь, я новичок в JavaScript и пытаюсь понять, как закодировать следующее, поскольку я застреваю, когда строка полезной нагрузки не является стандартной 8-битной 1-байтовой группой, поэтому я получаю 320-битный 40-байтовый массив. первые несколько значений можно извлечь, поскольку они составляют 16 бит, затем 8 бит, затем 32 бита информации, но следующее значение составляет всего 10 бит, и я застрял здесь. итак, я, вероятно, должен преобразовать 40 байтов в 320 бит, а затем сдвинуть вправо для каждого числа бит на переменную? я не уверен, как это сделать. Это мой формат полезной нагрузки, а в скобках указано количество битов для этой переменной. любая помощь будет оценена.

https://www.iotsoundsensor.com/wp-content/uploads/2021/11/310_payload_parser_manual.html

 function Decoder(bytes, port) {
  //8 bit single byte values
  var messageinfo = bytes[2]>>[2];
  
  var battery   = bytes[2]>>[0];
  var latitude  = bytes[4]>>[4];
  var longatude = bytes[4]>>[4];
  
  //now have 10 bit values to decode
  
  var LAfast    = bytes[15]>>>[0];
  var LAslow    = bytes[16]>>>[2];
  
  return {
    messageinfo: messageinfo,
    battery: battery/10, 
    LAfast : LAfast/10,
    LAslow : LAslow/10,
    latitude: latitude,
    longatude: longatude
    
  }
}
 

Комментарии:

1. Вы добавили тег javascript к своему вопросу, и в своем тексте вы написали java. Поэтому, пожалуйста, уточните, какой язык вы имеете в виду. Другое дело, исправьте пунктуацию вашего сообщения. Спасибо.

Ответ №1:

Я переписал Decode() функцию на основе кода JavaScript в iot-source (который на самом деле является библией для расшифровки этих сообщений).

Я создал getField() функцию для декодирования полей с заданным смещением, длиной и разрешением, а также getBits() функцию для извлечения массива битов для последующего декодирования (используется для полей LAxxx).

Я использовал пример со страницы выше в качестве входных данных для Decode():

 function hexToByteArray(hex) {
    return Array.from({ length: hex.length/2}, (v,n) => parseInt(hex.slice(n * 2, n*2   2), 16));
}

function getField(offset, length, bytes, resolution = 1) {
    return bytesToNum(bytes.slice(offset, offset   length)) * resolution;
}

function bytesToNum(bytes) {    
    return bytes.reduce((acc, b, x) => acc | (b << (x * 8)), 0);
}

// Convert a byte segment to bits
function getBits(offset, length, bytes) {
    return bytes.slice(offset, offset   length).map((byt) => { 
        return Array.from({ length: 8 }).map((x, i) => {
            return ((byt * (2 ** i) amp; 0x80) !== 0 ? 1 : 0);
        });
    }, []).flat();
}

function parseBits(bits) {
    return bits.reduce((acc, b, i) => {
        return acc   0.1*(bits[bits.length - 1 - i] ? 2**(i): 0); 
    }, 30);
}

function Decoder(bytes, port) {
  let offset = 0;
  let messageinfo = getField(offset, 2, bytes, 1);
  
  let battery   = getField(offset  = 2, 1, bytes, 0.1);
  // NB: We should check messageinfo to ensure these are actually present...
  let latitude  = getField(offset  = 1, 4, bytes, 1e-7);
  let longitude = getField(offset  = 4, 4, bytes, 1e-7);
  
  // Skip parsing timestamp for now...
  offset  = 4

  let bitArray = getBits(offset  = 4, 20, bytes);
    
  let bitIndex = 0;
  let LAfast = parseBits(bitArray.slice(bitIndex, bitIndex  = 10));
  let LAslow = parseBits(bitArray.slice(bitIndex, bitIndex  = 10));
  let LCfast = parseBits(bitArray.slice(bitIndex, bitIndex  = 10));
  let LCslow = parseBits(bitArray.slice(bitIndex, bitIndex  = 10));

  return {
    messageinfo,
    battery, 
    LAfast,
    LAslow,
    LCfast,
    LCslow,
    latitude,
    longitude
  }
}

let bytes = (hexToByteArray('7FFF3F6599341FE38C11036A608C60370DA561584699336CDB55CDB390F44BD4B5B9D5390E34BCE3'))
console.log(Decoder(bytes)) 
 .as-console-wrapper { max-height: 100% !important; top: 0; } 

Комментарии:

1. (v,k) => k) это уже функция картографирования. Так что вы можете написать здесь саму логику. Нет необходимости писать 2 функции сопоставления

2. Хорошая мысль @Rajesh!, теперь все проще, спасибо