预期第一层具有 x 维但得到一个形状为 y 的数组
expected first layer to have x dimensions but got an array with shape y
(我刚开始在节点上 tensorflow.js)
我一直在网上上下搜索答案。
困惑
我有来自 image1 = tf.fromPixels(img)
的图像数据,我尝试将它与其他图像数据一起输入到 xs = tf.tensor([image1, image2])
。令人困惑的是,无论我如何将一堆图像输入 xs
for model.fit
,程序都会输出如下所述的错误。
我已经尝试过的
当我 运行 程序时,我得到错误 Error: Error when checking input: expected conv2d_Conv2D1_input to have 4 dimension(s). but got array with shape 4,1
我知道我没有正确输入 xs。我在网上阅读了一些文章,内容涉及如何以 tf.tensor([[0.2, 0.1], [0.2, 0.4]]);
之类的方式输入数组以及某种图像的一些批处理。我看了一些文章,表明对于图像,您需要另一组图层:
model.add(tf.layers.conv2d({
inputShape: [scaleHeight, scaleWidth, 3],
kernelSize: 5,
filters: 8,
strides: 1,
activation: 'relu',
kernelInitializer: 'VarianceScaling'
}));
model.add(tf.layers.maxPooling2d({
poolSize: [2, 2],
strides: [2, 2]
}));
model.add(tf.layers.conv2d({
kernelSize: 5,
filters: 16,
strides: 1,
activation: 'relu',
kernelInitializer: 'VarianceScaling'
}));
model.add(tf.layers.maxPooling2d({
poolSize: [2, 2],
strides: [2, 2]
}));
model.add(tf.layers.dense({ // Output
units: 2,
kernelInitializer: 'VarianceScaling',
activation: 'softmax'
}));
model.compile({loss: 'categoricalCrossentropy', optimizer: tf.train.sgd(0.1), metrics: ['accuracy']});
好吧,我尝试输入它,尝试将它们转换成 typedarray 格式,尝试了很多东西。对于 tf.fromPixels(canvas)
为 model.fit(xs, ys, {epochs: 100, options....});
将多个图像转换为张量,我很迷茫想出一个合适的 xs 变量
代码:
var tf = require('@tensorflow/tfjs');
var cv = require('canvas');
var {Image, createCanvas, ImageData} = cv;
tf.disableDeprecationWarnings();
var scaleWidth = 16;
var scaleHeight = 16;
function getImage(path){
var img = new Image();
return new Promise(function(resolve, reject){
img.onload = function(){
var element = createCanvas(scaleWidth, scaleHeight);
var ctx = element.getContext('2d');
ctx.drawImage(img, 0, 0);
ctx.scale(scaleWidth/img.width, scaleHeight/img.height);
//resolve(Array.from(tf.fromPixels(element).flatten().dataSync()));
resolve(tf.fromPixels(element));
};
img.src = path;
});
}
var log = function(input){console.log(input)};
const model = tf.sequential();
model.add(tf.layers.conv2d({
inputShape: [scaleHeight, scaleWidth, 3],
kernelSize: 5,
filters: 8,
strides: 1,
activation: 'relu',
kernelInitializer: 'VarianceScaling'
}));
model.add(tf.layers.maxPooling2d({
poolSize: [2, 2],
strides: [2, 2]
}));
model.add(tf.layers.conv2d({
kernelSize: 5,
filters: 16,
strides: 1,
activation: 'relu',
kernelInitializer: 'VarianceScaling'
}));
model.add(tf.layers.maxPooling2d({
poolSize: [2, 2],
strides: [2, 2]
}));
model.add(tf.layers.dense({ // Output
units: 2,
kernelInitializer: 'VarianceScaling',
activation: 'softmax'
}));
model.compile({loss: 'categoricalCrossentropy', optimizer: tf.train.sgd(0.1), metrics: ['accuracy']});
(async function(){
var cats = [], bland = [];
cats[0] = await getImage('cats/0.jpeg');
cats[1] = await getImage('cats/1.jpeg');
bland[0] = await getImage('bland/0.png');
bland[1] = await getImage('bland/1.png');
var testCats = await getImage('c.jpeg');
var testBland = await getImage('b.jpeg');
var xs = tf.tensor([cats[0], cats[1], bland[0], bland[1]]); // confusion occurs here
for(var c = 0; c < 10; c++){
var result = await model.fit(xs, tf.tensor([[0, 1], [0, 1], [1, 0], [1, 0]]), {epochs: 100});
console.log(result.history.loss[0]);
}
})();
在我 运行 它之后,我希望至少记录模型的损失但是它抛出了这个错误:
Error: Error when checking input: expected conv2d_Conv2D1_input to have 4 dimension(s). but got array with shape 4,1
查看您的代码,传入模型的数据与模型第一层 inputShape 的形状不同。
如何着手解决问题?
- 检查 data.shape。
console.log(xs.shape) // it will return (4,1)
与输入形状比较
data shape应该比inputShape高一维(batchsize多一维)
// Does `xs.inputShape.slice(1) ===[Scaleheight, scaleWidth,3]` ?
shape1 = xs.inputShape.slice(1)
shape2 = [Scaleheight, scaleWidth,3]
const same = (shape1.length == shape2.length) && shape1.every(function(e, i) {
return e === shape2[i];
});
如果不相等,有两种方法可以解决问题
如果可能重塑数据,使用tf.reshape
、tf.slice
、tf.expandDims()
、...
或者简单地将 inputShape 更改为等于我们的数据形状
在你的例子中,输入形状和数据形状之间明显不匹配。
首先,你创建xs的方式是错误的。实际上,xs 具有 NaN 值的形状 (4, 1)。这就好像你创建了一个带有张量数组的 tf.tensor
。您可以这样创建 xs:
xs = tf.concat([...cats, ...blands], 0)
但是不确定这是否能彻底解决问题。您需要迭代上述步骤,即检查 xs 的形状,与 inputShape 进行比较等等...
(我刚开始在节点上 tensorflow.js)
我一直在网上上下搜索答案。
困惑
我有来自 image1 = tf.fromPixels(img)
的图像数据,我尝试将它与其他图像数据一起输入到 xs = tf.tensor([image1, image2])
。令人困惑的是,无论我如何将一堆图像输入 xs
for model.fit
,程序都会输出如下所述的错误。
我已经尝试过的
当我 运行 程序时,我得到错误 Error: Error when checking input: expected conv2d_Conv2D1_input to have 4 dimension(s). but got array with shape 4,1
我知道我没有正确输入 xs。我在网上阅读了一些文章,内容涉及如何以 tf.tensor([[0.2, 0.1], [0.2, 0.4]]);
之类的方式输入数组以及某种图像的一些批处理。我看了一些文章,表明对于图像,您需要另一组图层:
model.add(tf.layers.conv2d({
inputShape: [scaleHeight, scaleWidth, 3],
kernelSize: 5,
filters: 8,
strides: 1,
activation: 'relu',
kernelInitializer: 'VarianceScaling'
}));
model.add(tf.layers.maxPooling2d({
poolSize: [2, 2],
strides: [2, 2]
}));
model.add(tf.layers.conv2d({
kernelSize: 5,
filters: 16,
strides: 1,
activation: 'relu',
kernelInitializer: 'VarianceScaling'
}));
model.add(tf.layers.maxPooling2d({
poolSize: [2, 2],
strides: [2, 2]
}));
model.add(tf.layers.dense({ // Output
units: 2,
kernelInitializer: 'VarianceScaling',
activation: 'softmax'
}));
model.compile({loss: 'categoricalCrossentropy', optimizer: tf.train.sgd(0.1), metrics: ['accuracy']});
好吧,我尝试输入它,尝试将它们转换成 typedarray 格式,尝试了很多东西。对于 tf.fromPixels(canvas)
为 model.fit(xs, ys, {epochs: 100, options....});
代码:
var tf = require('@tensorflow/tfjs');
var cv = require('canvas');
var {Image, createCanvas, ImageData} = cv;
tf.disableDeprecationWarnings();
var scaleWidth = 16;
var scaleHeight = 16;
function getImage(path){
var img = new Image();
return new Promise(function(resolve, reject){
img.onload = function(){
var element = createCanvas(scaleWidth, scaleHeight);
var ctx = element.getContext('2d');
ctx.drawImage(img, 0, 0);
ctx.scale(scaleWidth/img.width, scaleHeight/img.height);
//resolve(Array.from(tf.fromPixels(element).flatten().dataSync()));
resolve(tf.fromPixels(element));
};
img.src = path;
});
}
var log = function(input){console.log(input)};
const model = tf.sequential();
model.add(tf.layers.conv2d({
inputShape: [scaleHeight, scaleWidth, 3],
kernelSize: 5,
filters: 8,
strides: 1,
activation: 'relu',
kernelInitializer: 'VarianceScaling'
}));
model.add(tf.layers.maxPooling2d({
poolSize: [2, 2],
strides: [2, 2]
}));
model.add(tf.layers.conv2d({
kernelSize: 5,
filters: 16,
strides: 1,
activation: 'relu',
kernelInitializer: 'VarianceScaling'
}));
model.add(tf.layers.maxPooling2d({
poolSize: [2, 2],
strides: [2, 2]
}));
model.add(tf.layers.dense({ // Output
units: 2,
kernelInitializer: 'VarianceScaling',
activation: 'softmax'
}));
model.compile({loss: 'categoricalCrossentropy', optimizer: tf.train.sgd(0.1), metrics: ['accuracy']});
(async function(){
var cats = [], bland = [];
cats[0] = await getImage('cats/0.jpeg');
cats[1] = await getImage('cats/1.jpeg');
bland[0] = await getImage('bland/0.png');
bland[1] = await getImage('bland/1.png');
var testCats = await getImage('c.jpeg');
var testBland = await getImage('b.jpeg');
var xs = tf.tensor([cats[0], cats[1], bland[0], bland[1]]); // confusion occurs here
for(var c = 0; c < 10; c++){
var result = await model.fit(xs, tf.tensor([[0, 1], [0, 1], [1, 0], [1, 0]]), {epochs: 100});
console.log(result.history.loss[0]);
}
})();
在我 运行 它之后,我希望至少记录模型的损失但是它抛出了这个错误:Error: Error when checking input: expected conv2d_Conv2D1_input to have 4 dimension(s). but got array with shape 4,1
查看您的代码,传入模型的数据与模型第一层 inputShape 的形状不同。
如何着手解决问题?
- 检查 data.shape。
console.log(xs.shape) // it will return (4,1)
与输入形状比较
data shape应该比inputShape高一维(batchsize多一维)
// Does `xs.inputShape.slice(1) ===[Scaleheight, scaleWidth,3]` ?
shape1 = xs.inputShape.slice(1)
shape2 = [Scaleheight, scaleWidth,3]
const same = (shape1.length == shape2.length) && shape1.every(function(e, i) {
return e === shape2[i];
});
如果不相等,有两种方法可以解决问题
如果可能重塑数据,使用
tf.reshape
、tf.slice
、tf.expandDims()
、...或者简单地将 inputShape 更改为等于我们的数据形状
在你的例子中,输入形状和数据形状之间明显不匹配。
首先,你创建xs的方式是错误的。实际上,xs 具有 NaN 值的形状 (4, 1)。这就好像你创建了一个带有张量数组的 tf.tensor
。您可以这样创建 xs:
xs = tf.concat([...cats, ...blands], 0)
但是不确定这是否能彻底解决问题。您需要迭代上述步骤,即检查 xs 的形状,与 inputShape 进行比较等等...