How to get/set weights for a supervised model in tensorflow.js?

混江龙づ霸主 提交于 2021-02-10 07:53:15

问题


I'd like to change the weights of a supervised model but I get the same exact result after changing the weights. What am I doing wrong?

const model = tf.sequential();
model.add(tf.layers.dense({...}));
model.add(tf.layers.dense({...}));
model.add(tf.layers.dense({...}));
model.compile({...});
model.fit({});

const result1 = model.predict(tf.tensor2d(...)).dataSync();

const newWeights = [];
model.layers.map((layer, i) => {
  newWeights[i] = []
  const weights = layer.getWeights();
  newWeights[i][0] = weights[0].arraySync()
  newWeights[i][1] = weights[1].arraySync()

  newWeights[i][0].map(tensor => tensor.map(x => {
    if (random(1) < 0.5) {
      return x + offset();
    }

    return x;
  })

  layer.setWeights([tf.tensor2d(newWeights[i][0], [newWeights[i][0].length, newWeights[i][0][0].length]), tf.tensor(newWeights[i][1])])
})

const result2 = model.predict(tf.tensor2d(...)).dataSync();

Code snippets:

const random = (max) => {
  return floor(Math.random() * Math.floor(max), 2);
} 

const floor = (num, toDecimal) => {
  let  dec = Math.pow(10, toDecimal);
  return Number(Math.floor(num * dec) / dec);
}

const offset = () => {
  randomGaussian() * 0.5
}

let previous = false;
let y2 = 0;
const randomGaussian = (mean, sd) => {
  let y1, x1, x2, w;
  if (previous) {
    y1 = y2;
    previous = false;
  } else {
    do {
      x1 = random(2) - 1;
      x2 = random(2) - 1;
      w = x1 * x1 + x2 * x2;
    } while (w >= 1);
    w = Math.sqrt(-2 * Math.log(w) / w);
    y1 = x1 * w;
    y2 = x2 * w;
    previous = true;
  }

  let m = mean || 0;
  let s = sd || 1;
  return y1 * s + m;
};

result1 === result2 but why?


回答1:


Most likely that the new weights are identical to that of the first model.

Example: Simple example to change weights of a model

(async() => {
const model = tf.sequential({
        layers: [tf.layers.dense({units: 1, inputShape: [10]})]
    });
    model.compile({optimizer: 'sgd', loss: 'meanSquaredError'});
    for (let i = 1; i < 5 ; ++i) {
      const h = await model.fit(tf.ones([8, 10]), tf.ones([8, 1]), {
          batchSize: 4,
          epochs: 3
      });
      console.log("Loss after Epoch " + i + " : " + h.history.loss[0]);
    }
    
    const p = await model.predict(tf.zeros([1, 10]))
    p.print()
    const layers = model.layers

    layers[0].setWeights([tf.zeros([10, 1]), tf.zeros([1])])
    
    const q = await model.predict(tf.zeros([1, 10]))
    q.print()


})()
<html>
  <head>
    <!-- Load TensorFlow.js -->
    <script src="https://cdn.jsdelivr.net/npm/@tensorflow/tfjs@latest"> </script>
  </head>

  <body>
  </body>
</html>

Issue of the code

The newWeights created is not assigned to newWeights. map is not an in-place operator. The array returned by map should be assigned back to newWeights.

newWeights[i][0] = newWeights[i][0].map(tensor => tensor.map(x => {
    if (random(1) < 0.5) {
      return x + offset();
    }

    return x;
  })


来源:https://stackoverflow.com/questions/57917450/how-to-get-set-weights-for-a-supervised-model-in-tensorflow-js

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!