调用dispose后未知的遗留张量



由于我刚刚开始使用TensorFlow.js学习ML,我想获得一些实践经验,并提出了以下代码,试图解决异或问题(当然失败了)。

const tf = require('@tensorflow/tfjs');
require('@tensorflow/tfjs-node');
const dataset_train = [
{ a1: .2, a2: .1, a3: .65, b1: .35, b2: .55, result: 0 },
{ a1: .05, a2: 0, a3: .1, b1: .5, b2: .4, result: 1 },
{ a1: .8, a2: .15, a3: .05, b1: .15, b2: .1, result: 1 },
{ a1: 0, a2: .05, a3: .1, b1: .45, b2: .45, result: 1 },
{ a1: .15, a2: .05, a3: .75, b1: .4, b2: .35, result: 0 },
{ a1: .2, a2: .05, a3: 0, b1: .15, b2: 0, result: 0 },
{ a1: .1, a2: .1, a3: .05, b1: .65, b2: .25, result: 1 },
{ a1: .8, a2: 0, a3: .05, b1: .25, b2: .1, result: 1 },
{ a1: .15, a2: .05, a3: 0, b1: 0, b2: .15, result: 0 },
{ a1: .4, a2: .15, a3: .2, b1: .7, b2: .3, result: 0 }
];
const dataset_validation = [
{ a1: 0, a2: .15, a3: .1, b1: .25, b2: .7, result: 1 },
{ a1: .9, a2: .05, a3: 0, b1: .3, b2: .7, result: 0 },
{ a1: .15, a2: 0, a3: .05, b1: .2, b2: .1, result: 0 },
{ a1: .6, a2: .25, a3: .1, b1: .05, b2: 0, result: 1 },
{ a1: .05, a2: .45, a3: .35, b1: .6, b2: .3, result: 0 }
];
const dataset_test = [
{ a1: .25, a2: .5, a3: .15, b1: .05, b2: .1 },
{ a1: .05, a2: 0, a3: 0, b1: .8, b2: 0 },
{ a1: 0, a2: .1, a3: .05, b1: .1, b2: .15 },
{ a1: .3, a2: .45, a3: .25, b1: .25, b2: .7 },
{ a1: 0, a2: .15, a3: 0, b1: .45, b2: .35 }
];
const input_1 = tf.input({ shape: [3] });
const input_2 = tf.input({ shape: [2] });
const layer_1_1 = tf.layers.dense({ units: 3, activation: 'sigmoid' }).apply(input_1);
const layer_1_2 = tf.layers.dense({ units: 2, activation: 'sigmoid' }).apply(input_2);
const layer_2_1 = tf.layers.concatenate().apply([layer_1_1, layer_1_2]);
const layer_3_1 = tf.layers.dense({ units: 5, activation: 'sigmoid' }).apply(layer_2_1);
const layer_4_1 = tf.layers.dense({ units: 1, activation: 'sigmoid' }).apply(layer_3_1);
const model = tf.model({ inputs: [input_1, input_2], outputs: layer_4_1 });
const x_train_1 = tf.tensor(dataset_train.map(d => [d.a1, d.a2, d.a3]));
const x_train_2 = tf.tensor(dataset_train.map(d => [d.b1, d.b2]));
const y_train = tf.tensor(dataset_train.map(d => [d.result]));
const x_valid_1 = tf.tensor(dataset_validation.map(d => [d.a1, d.a2, d.a3]));
const x_valid_2 = tf.tensor(dataset_validation.map(d => [d.b1, d.b2]));
const y_valid = tf.tensor(dataset_validation.map(d => [d.result]));
const x_test_1 = tf.tensor(dataset_test.map(d => [d.a1, d.a2, d.a3]));
const x_test_2 = tf.tensor(dataset_test.map(d => [d.b1, d.b2]));
const tensors = [
x_train_1,
x_train_2,
y_train,
x_valid_1,
x_valid_2,
y_valid,
x_test_1,
x_test_2
];
model.compile({ optimizer: 'sgd', loss: 'meanSquaredError' });
model.fit([x_train_1, x_train_2], y_train, {
epochs: 1000,
batchSize: 20,
shuffle: true,
validationData: [[x_valid_1, x_valid_2], y_valid]
}).then(() => {
model.predict([x_test_1, x_test_2]).print();
for (let i = 0; i < tensors.length; ++i) {
tensors[i].dispose();
}
tf.disposeVariables();
// 2 tensors are still lingering somewhere...
console.log(`${JSON.stringify(tf.memory())}`);
});

代码在我的Windows 10机器上的Node.js控制台中执行。预测完成后,内存使用情况将打印到控制台,如下所示。

{"unreliable":true,"numTensors":2,"numDataBuffers":2,"numBytes":24}

  • 这些遗留张量的来源是什么?
  • 我该如何处理?

当你调用model.predict(...)时,你创建了一个需要被处置的新张量(即使你没有将其分配为变量)。我相信另一个和你的型号是一致的。注意,当您在模型上调用.dispose()时,您不需要也调用tf.disposeVariables()。我重新运行你的代码,修改如下:

const output = model.predict([x_test_1, x_test_2]);
output.print();
output.dispose();  <---
model.dispose();   <---
for (let i = 0; i < tensors.length; ++i) {
tensors[i].dispose();
}
console.log(`${JSON.stringify(tf.memory())}`);

输出如下:

{"unreliable":true,"numTensors":0,"numDataBuffers":0,"numBytes":0}

最新更新