Tensorflow无法预测足够准确的结果

时间:2018-05-16 22:33:14

标签: python tensorflow machine-learning tensorflow-datasets

我对我在Tensorflow项目中选择的算法有一些基本的问题。我输入了大约100万套训练数据,仍然无法获得足够准确的预测结果。

我使用的代码基于旧的Tensorflow示例(https://github.com/tensorflow/tensorflow/blob/r1.3/tensorflow/examples/tutorials/estimators/abalone.py)。此示例的目标是根据提供的培训功能预测鲍鱼的年龄。

我的目的非常相似。唯一的区别是我有更多的标签(6)与我的功能(4)相比。由于培训后的预测很少,因此对该项目可行性的关注开始引起一些担忧。

我是机器学习和Tensorflow的新手,所以我不太确定我是否为这个项目选择了正确的方法。我想知道是否有一些方法可以改进我当前的代码,以提高预测的准确性,如更多层,不同的优化方法等。

以下是代码:

from __future__ import absolute_import
from __future__ import division
from __future__ import print_function

import argparse
import sys
import numpy as np

import pandas as pd
import tensorflow as tf

LEARNING_RATE = 0.001


def model_fn(features, labels, mode, params):
  """Model function for Estimator."""

  first_hidden_layer = tf.layers.dense(features["x"], 10, activation=tf.nn.relu)

  # Connect the second hidden layer to first hidden layer with relu
  second_hidden_layer = tf.layers.dense(
      first_hidden_layer, 10, activation=tf.nn.relu)

  # Connect the output layer to second hidden layer (no activation fn)
  output_layer = tf.layers.dense(second_hidden_layer, 6)

  # Reshape output layer to 1-dim Tensor to return predictions
  predictions = tf.reshape(output_layer, [-1,6])

  # Provide an estimator spec for `ModeKeys.PREDICT`.
  if mode == tf.estimator.ModeKeys.PREDICT:
    return tf.estimator.EstimatorSpec(
        mode=mode,
        predictions={"ages": predictions})

  # Calculate loss using mean squared error
  loss = tf.losses.mean_squared_error(labels, predictions)

  optimizer = tf.train.GradientDescentOptimizer(
      learning_rate=params["learning_rate"])
  train_op = optimizer.minimize(
      loss=loss, global_step=tf.train.get_global_step())

  # Calculate root mean squared error as additional eval metric
  eval_metric_ops = {
      "rmse": tf.metrics.root_mean_squared_error(
          tf.cast(labels, tf.float64), predictions)
  }

  # Provide an estimator spec for `ModeKeys.EVAL` and `ModeKeys.TRAIN` modes.
  return tf.estimator.EstimatorSpec(
      mode=mode,
      loss=loss,
      train_op=train_op,
      eval_metric_ops=eval_metric_ops)


def main(unused_argv):

  train_file = "training_data_mc1000.csv"
  test_file = "test_data_mc1000.csv"

  train_features_interim = pd.read_csv(train_file, usecols=['vgs', 'vbs', 'vds', 'current'])
  train_features_numpy = np.asarray(train_features_interim, dtype=np.float64)

  train_labels_interim = pd.read_csv(train_file, usecols=['plo_tox', 'plo_dxl', 'plo_dxw', 'parl1', 'parl2', 'random_fn'])
  train_labels_numpy = np.asarray(train_labels_interim, dtype=np.float64)

  # Set model params
  model_params = {"learning_rate": LEARNING_RATE}

  # Instantiate Estimator
  nn = tf.estimator.Estimator(model_fn=model_fn, params=model_params)

  train_input_fn = tf.estimator.inputs.numpy_input_fn(
      x={"x": train_features_numpy},
      y=train_labels_numpy,
      num_epochs=None,
      shuffle=True)

  # Train
  nn.train(input_fn=train_input_fn, max_steps=1048576)

  test_features_interim = pd.read_csv(test_file, usecols=['vgs', 'vbs', 'vds', 'current'])
  test_features_numpy = np.asarray(test_features_interim, dtype=np.float64)

  test_labels_interim = pd.read_csv(test_file, usecols=['plo_tox', 'plo_dxl', 'plo_dxw', 'parl1', 'parl2', 'random_fn'])
  test_labels_numpy = np.asarray(test_labels_interim, dtype=np.float64)

  # Score accuracy
  test_input_fn = tf.estimator.inputs.numpy_input_fn(
      x={"x": test_features_numpy},
      y=test_labels_numpy,
      num_epochs=1,
      shuffle=False)

  ev = nn.evaluate(input_fn=test_input_fn)
  print("Loss: %s" % ev["loss"])
  print("Root Mean Squared Error: %s" % ev["rmse"])

  prediction_file = "Tensorflow_prediction_data.csv"

  predict_features_interim = pd.read_csv(prediction_file, usecols=['vgs', 'vbs', 'vds', 'current'])
  predict_features_numpy = np.asarray(predict_features_interim, dtype=np.float64)

  # Print out predictions
  predict_input_fn = tf.estimator.inputs.numpy_input_fn(
      x= {"x": predict_features_numpy},
      num_epochs=1,
      shuffle=False)
  predictions = nn.predict(input_fn=predict_input_fn)
  for i, p in enumerate(predictions):
    print("Prediction %s: %s" % (i + 1, p["ages"]))


if __name__ == '__main__':
  tf.logging.set_verbosity(tf.logging.INFO)
  parser = argparse.ArgumentParser()
  parser.register("type", "bool", lambda v: v.lower() == "true")
  parser.add_argument(
      "--train_data", type=str, default="", help="Path to the training data.")
  parser.add_argument(
      "--test_data", type=str, default="", help="Path to the test data.")
  parser.add_argument(
      "--predict_data",
      type=str,
      default="",
      help="Path to the prediction data.")
  FLAGS, unparsed = parser.parse_known_args()
  tf.app.run(main=main, argv=[sys.argv[0]] + unparsed)

部分培训和测试数据看起来像 enter image description here

最后四列是功能,前六列是标签。再次,你可以看到我有更多的标签而不是功能。我的目标是训练一个模型,当我提供新的功能集时,它可以预测足够准确的标签。

添加以下部分以澄清我的数据集。感谢第一批评论我的问题,提醒我也要提出这个问题。

我的功能和标签之间的关系是:每30(vgs)X10(vbs)X10(vds)对应1组标签。基本上它就像一个三维数组,前三个特征就像坐标一样,最后一个特征(当前)就像存储在每个单元格中的值一样。这就是为什么我展示的部分标签都是一样的。

现在的另一个问题是,我预计随着训练的进行,损失应该越来越小,但事实并非如此。我认为这应该是输出不准确的另一个原因,因为最小化损失部分不起作用。不过,我真的不知道为什么。

感谢您花时间看这个,我很乐意在下面进行讨论。

1 个答案:

答案 0 :(得分:1)

从我在代码中看到的内容来看,您没有规范化您的功能。尝试对它们进行标准化,例如使其均值为零且std = 1。由于您的功能处于完全不同的范围,因此这种规范化可能会有所帮助。

查看其他标签也很有帮助。提供的图片中的图片都是一样的。