Problem/error 'Property ''xs' 在 angular 项目 tensorflow.js 的类型 'TensorContainer' 上不存在
Problem/error 'Property ''xs' does not exist on type 'TensorContainer' in angular project with tensorflow.js
我正在尝试从我现有的 angular 项目中的 tensorflow.js-网站 运行 获取 tensorflow.js 示例。我基本上是从网站上复制代码并将其集成到我的组件中,但我收到一条错误消息。
由于我是 angular 的新手,所以我不知道如何修复错误。
export class MotionAnalysisComponent implements OnInit{
async run() {
// We want to predict the column "medv", which represents a median value of
// a home (in 00s), so we mark it as a label.
const csvUrl = 'https://storage.googleapis.com/tfjs-examples/multivariate-linear-regression/data/boston-housing-train.csv';
const csvDataset = tf.data.csv(
csvUrl, {
columnConfigs: {
medv: {
isLabel: true
}
}
});
// Number of features is the number of column names minus one for the label column.
const numOfFeatures = (await csvDataset.columnNames()).length - 1;
// Prepare the Dataset for training.
const flattenedDataset =
csvDataset
.map(({xs, ys}) =>
{
// Convert xs(features) and ys(labels) from object form (keyed by
// column name) to array form.
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
.batch(10);
// Define the model.
const model = tf.sequential();
model.add(tf.layers.dense({
inputShape: [numOfFeatures],
units: 1
}));
model.compile({
optimizer: tf.train.sgd(0.000001),
loss: 'meanSquaredError'
});
// Fit the model using the prepared Dataset
return model.fitDataset(flattenedDataset, {
epochs: 10,
callbacks: {
onEpochEnd: async (epoch, logs) => {
console.log(epoch + ':' + logs.loss);
}
}
});
}
}
我收到以下两条错误消息:
Property 'xs' does not exist on type 'TensorContainer'
Property 'ys' does not exist on type 'TensorContainer'
可以通过将 map 参数设置为 any
来避免打字错误
然后您需要强制转换 xs
和 ys
以允许类型完成。这里 xs
和 ys
只是键值元素的对象。
.map((val: any) => {
const {xs, ys} = val // can cast xs and ys to appropriate type
// for instance it can be const {xs, ys} = val as {xs: Object, ys: Object}
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
或者也可以通过转换map
的类型-参数来避免
.map((val: {xs: Object, ys: Object}) => {
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
要彻底xs
和ys
应该分别有数据集的特征类型和标签。
给定boston-housing.csv的数据,类型Features可以如下
interface Features {
crim: number;
zn: number;
inus: number
...
}
以及标签类型
interface Features {
medv: number
}
使用这些类型进行转换,如有必要,前面的代码将在 xs 和 ys 上自动完成 属性
.map((val: any) => {
const {xs, ys} = val as {xs: Features, ys: Labels}
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
// or
.map(((val: {xs: Features, ys: Labels }) => {
const {xs, ys} = val as {xs: Features, ys: Labels}
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
当然,在这些场景中准确键入特征或标签并没有多大用处,因为人们只对返回数据集的值感兴趣。如果要将此方法用作将 csv 数据集转换为张量批次的通用方法,则留下 xs
和 ys
类型 Object
应该是可行的方法。
更进一步,如果创建的数据集的类型与 csv 的字段完全匹配,则可能会为数据集创建 dataType
interface DataType {
xs: Features;
ys: Labels;
}
const csvDataset = tf.data.csv(/* ... */) as unknown as Dataset<DataType>;
问题
问题是您的数据集 Datasets in Tensorflow.js are by default of type tf.data.Dataset<TensorContainer>
, which means that TypeScript assumes an object of TensorContainer
。
解决方案
为了帮助 TypeScript,您可以在创建 DataSet 时为其指定特定类型。当您正在读取内部具有多个属性的对象时,您可以扩展接口 TensorContainerObject
.
代码示例
import { TensorContainerObject } from '@tensorflow/tfjs';
import { Dataset } from '@tensorflow/tfjs-data';
interface DataType extends TensorContainerObject {
xs: tf.Tensor;
ys: tf.Tensor;
}
const csvDataset = tf.data.csv(/* ... */) as any as Dataset<DataType>;
csvDataset.map(({xs, ys}) => {
// ...
});
不幸的是,由于 Tensorflow.js 对其数据集类型非常自以为是(因为联合用于默认 TensorContainer
),您必须先使用 any
强制转换将其转换为实际的 Dataset<DataType>
界面。
但是在转换之后,所有在 DataSet
上工作的函数,如 map
都会自动知道正确的类型。除了使用上面的 tf.Tensor
,您甚至可以使用 tf.Tensor1D
这样的类型来更加具体。
替代解决方案:让错误消失
正如其他答案中所述:如果您不关心类型和 TypeScript,只想让错误消失,您可以将任何有问题的变量转换为 any
.
代码示例
csvDataset.map(({xs, ys}: any) => {
// ...
});
请记住,这将禁用对变量的任何类型检查。
我正在尝试从我现有的 angular 项目中的 tensorflow.js-网站 运行 获取 tensorflow.js 示例。我基本上是从网站上复制代码并将其集成到我的组件中,但我收到一条错误消息。
由于我是 angular 的新手,所以我不知道如何修复错误。
export class MotionAnalysisComponent implements OnInit{
async run() {
// We want to predict the column "medv", which represents a median value of
// a home (in 00s), so we mark it as a label.
const csvUrl = 'https://storage.googleapis.com/tfjs-examples/multivariate-linear-regression/data/boston-housing-train.csv';
const csvDataset = tf.data.csv(
csvUrl, {
columnConfigs: {
medv: {
isLabel: true
}
}
});
// Number of features is the number of column names minus one for the label column.
const numOfFeatures = (await csvDataset.columnNames()).length - 1;
// Prepare the Dataset for training.
const flattenedDataset =
csvDataset
.map(({xs, ys}) =>
{
// Convert xs(features) and ys(labels) from object form (keyed by
// column name) to array form.
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
.batch(10);
// Define the model.
const model = tf.sequential();
model.add(tf.layers.dense({
inputShape: [numOfFeatures],
units: 1
}));
model.compile({
optimizer: tf.train.sgd(0.000001),
loss: 'meanSquaredError'
});
// Fit the model using the prepared Dataset
return model.fitDataset(flattenedDataset, {
epochs: 10,
callbacks: {
onEpochEnd: async (epoch, logs) => {
console.log(epoch + ':' + logs.loss);
}
}
});
}
}
我收到以下两条错误消息:
Property 'xs' does not exist on type 'TensorContainer'
Property 'ys' does not exist on type 'TensorContainer'
可以通过将 map 参数设置为 any
然后您需要强制转换 xs
和 ys
以允许类型完成。这里 xs
和 ys
只是键值元素的对象。
.map((val: any) => {
const {xs, ys} = val // can cast xs and ys to appropriate type
// for instance it can be const {xs, ys} = val as {xs: Object, ys: Object}
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
或者也可以通过转换map
.map((val: {xs: Object, ys: Object}) => {
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
要彻底xs
和ys
应该分别有数据集的特征类型和标签。
给定boston-housing.csv的数据,类型Features可以如下
interface Features {
crim: number;
zn: number;
inus: number
...
}
以及标签类型
interface Features {
medv: number
}
使用这些类型进行转换,如有必要,前面的代码将在 xs 和 ys 上自动完成 属性
.map((val: any) => {
const {xs, ys} = val as {xs: Features, ys: Labels}
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
// or
.map(((val: {xs: Features, ys: Labels }) => {
const {xs, ys} = val as {xs: Features, ys: Labels}
return {xs:Object.keys(xs), ys:Object.keys(ys)};
})
当然,在这些场景中准确键入特征或标签并没有多大用处,因为人们只对返回数据集的值感兴趣。如果要将此方法用作将 csv 数据集转换为张量批次的通用方法,则留下 xs
和 ys
类型 Object
应该是可行的方法。
更进一步,如果创建的数据集的类型与 csv 的字段完全匹配,则可能会为数据集创建 dataType
interface DataType {
xs: Features;
ys: Labels;
}
const csvDataset = tf.data.csv(/* ... */) as unknown as Dataset<DataType>;
问题
问题是您的数据集 Datasets in Tensorflow.js are by default of type tf.data.Dataset<TensorContainer>
, which means that TypeScript assumes an object of TensorContainer
。
解决方案
为了帮助 TypeScript,您可以在创建 DataSet 时为其指定特定类型。当您正在读取内部具有多个属性的对象时,您可以扩展接口 TensorContainerObject
.
代码示例
import { TensorContainerObject } from '@tensorflow/tfjs';
import { Dataset } from '@tensorflow/tfjs-data';
interface DataType extends TensorContainerObject {
xs: tf.Tensor;
ys: tf.Tensor;
}
const csvDataset = tf.data.csv(/* ... */) as any as Dataset<DataType>;
csvDataset.map(({xs, ys}) => {
// ...
});
不幸的是,由于 Tensorflow.js 对其数据集类型非常自以为是(因为联合用于默认 TensorContainer
),您必须先使用 any
强制转换将其转换为实际的 Dataset<DataType>
界面。
但是在转换之后,所有在 DataSet
上工作的函数,如 map
都会自动知道正确的类型。除了使用上面的 tf.Tensor
,您甚至可以使用 tf.Tensor1D
这样的类型来更加具体。
替代解决方案:让错误消失
正如其他答案中所述:如果您不关心类型和 TypeScript,只想让错误消失,您可以将任何有问题的变量转换为 any
.
代码示例
csvDataset.map(({xs, ys}: any) => {
// ...
});
请记住,这将禁用对变量的任何类型检查。