通过 feature_columns 使用数据集 API 将自由文本功能引入 Tensorflow Canned Estimators
Getting free text features into Tensorflow Canned Estimators with Dataset API via feature_columns
我正在尝试构建一个模型,它给出 reddit_score = f('subreddit','comment')
这主要是作为一个例子,我可以以此为基础构建一个工作项目。
我的密码是here.
我的问题是我看到罐头估算器,例如DNNLinearCombinedRegressor 必须有 feature_columns 是 FeatureColumn
class 的一部分。
我有我的词汇文件,并且知道如果我只限制评论的第一个词,我可以做类似
的事情
tf.feature_column.categorical_column_with_vocabulary_file(
key='comment',
vocabulary_file='{}/vocab.csv'.format(INPUT_DIR)
)
但是如果我传递的是评论中的前 10 个词,那么我不确定如何从 "this is a pre padded 10 word comment xyzpadxyz xyzpadxyz"
之类的字符串转换为 feature_column
这样我就可以构建传递给广度和深度模型中的 deep
特征的嵌入。
看起来它一定是非常明显或简单的东西,但我终其一生都找不到任何具有此特定设置的现有示例(广度和深度罐装,数据集 api,以及功能,例如 subreddit 和评论等原始文本功能)。
我什至在考虑自己进行词汇整数查找,这样我传入的 comment
功能将类似于 [23,45,67,12,1,345,7,99,999,999] 然后也许我可以通过 numeric_feature 获得它的形状,然后从那里做一些事情。但这感觉有点奇怪。
您可以使用 tf.string_split(),然后执行 tf.slice() 对其进行切片,注意首先 tf.pad() 带有零的字符串。看标题中的预处理操作:
https://towardsdatascience.com/how-to-do-text-classification-using-tensorflow-word-embeddings-and-cnn-edae13b3e575
有了词,就可以创建十个特征栏
按照 post @Lak 的方法添加答案,但对数据集 api 做了一些调整。
# Create an input function reading a file using the Dataset API
# Then provide the results to the Estimator API
def read_dataset(prefix, mode, batch_size):
def _input_fn():
def decode_csv(value_column):
columns = tf.decode_csv(value_column, field_delim='|', record_defaults=DEFAULTS)
features = dict(zip(CSV_COLUMNS, columns))
features['comment_words'] = tf.string_split([features['comment']])
features['comment_words'] = tf.sparse_tensor_to_dense(features['comment_words'], default_value=PADWORD)
features['comment_padding'] = tf.constant([[0,0],[0,MAX_DOCUMENT_LENGTH]])
features['comment_padded'] = tf.pad(features['comment_words'], features['comment_padding'])
features['comment_sliced'] = tf.slice(features['comment_padded'], [0,0], [-1, MAX_DOCUMENT_LENGTH])
features['comment_words'] = tf.pad(features['comment_sliced'], features['comment_padding'])
features['comment_words'] = tf.slice(features['comment_words'],[0,0],[-1,MAX_DOCUMENT_LENGTH])
features.pop('comment_padding')
features.pop('comment_padded')
features.pop('comment_sliced')
label = features.pop(LABEL_COLUMN)
return features, label
# Use prefix to create file path
file_path = '{}/{}*{}*'.format(INPUT_DIR, prefix, PATTERN)
# Create list of files that match pattern
file_list = tf.gfile.Glob(file_path)
# Create dataset from file list
dataset = (tf.data.TextLineDataset(file_list) # Read text file
.map(decode_csv)) # Transform each elem by applying decode_csv fn
tf.logging.info("...dataset.output_types={}".format(dataset.output_types))
tf.logging.info("...dataset.output_shapes={}".format(dataset.output_shapes))
if mode == tf.estimator.ModeKeys.TRAIN:
num_epochs = None # indefinitely
dataset = dataset.shuffle(buffer_size = 10 * batch_size)
else:
num_epochs = 1 # end-of-input after this
dataset = dataset.repeat(num_epochs).batch(batch_size)
return dataset.make_one_shot_iterator().get_next()
return _input_fn
然后在下面的函数中,我们可以引用我们在 decode_csv()
中创建的字段:
# Define feature columns
def get_wide_deep():
EMBEDDING_SIZE = 10
# Define column types
subreddit = tf.feature_column.categorical_column_with_vocabulary_list('subreddit', ['news', 'ireland', 'pics'])
comment_embeds = tf.feature_column.embedding_column(
categorical_column = tf.feature_column.categorical_column_with_vocabulary_file(
key='comment_words',
vocabulary_file='{}/vocab.csv-00000-of-00001'.format(INPUT_DIR),
vocabulary_size=100
),
dimension = EMBEDDING_SIZE
)
# Sparse columns are wide, have a linear relationship with the output
wide = [ subreddit ]
# Continuous columns are deep, have a complex relationship with the output
deep = [ comment_embeds ]
return wide, deep
我正在尝试构建一个模型,它给出 reddit_score = f('subreddit','comment')
这主要是作为一个例子,我可以以此为基础构建一个工作项目。
我的密码是here.
我的问题是我看到罐头估算器,例如DNNLinearCombinedRegressor 必须有 feature_columns 是 FeatureColumn
class 的一部分。
我有我的词汇文件,并且知道如果我只限制评论的第一个词,我可以做类似
的事情tf.feature_column.categorical_column_with_vocabulary_file(
key='comment',
vocabulary_file='{}/vocab.csv'.format(INPUT_DIR)
)
但是如果我传递的是评论中的前 10 个词,那么我不确定如何从 "this is a pre padded 10 word comment xyzpadxyz xyzpadxyz"
之类的字符串转换为 feature_column
这样我就可以构建传递给广度和深度模型中的 deep
特征的嵌入。
看起来它一定是非常明显或简单的东西,但我终其一生都找不到任何具有此特定设置的现有示例(广度和深度罐装,数据集 api,以及功能,例如 subreddit 和评论等原始文本功能)。
我什至在考虑自己进行词汇整数查找,这样我传入的 comment
功能将类似于 [23,45,67,12,1,345,7,99,999,999] 然后也许我可以通过 numeric_feature 获得它的形状,然后从那里做一些事情。但这感觉有点奇怪。
您可以使用 tf.string_split(),然后执行 tf.slice() 对其进行切片,注意首先 tf.pad() 带有零的字符串。看标题中的预处理操作: https://towardsdatascience.com/how-to-do-text-classification-using-tensorflow-word-embeddings-and-cnn-edae13b3e575
有了词,就可以创建十个特征栏
按照 post @Lak 的方法添加答案,但对数据集 api 做了一些调整。
# Create an input function reading a file using the Dataset API
# Then provide the results to the Estimator API
def read_dataset(prefix, mode, batch_size):
def _input_fn():
def decode_csv(value_column):
columns = tf.decode_csv(value_column, field_delim='|', record_defaults=DEFAULTS)
features = dict(zip(CSV_COLUMNS, columns))
features['comment_words'] = tf.string_split([features['comment']])
features['comment_words'] = tf.sparse_tensor_to_dense(features['comment_words'], default_value=PADWORD)
features['comment_padding'] = tf.constant([[0,0],[0,MAX_DOCUMENT_LENGTH]])
features['comment_padded'] = tf.pad(features['comment_words'], features['comment_padding'])
features['comment_sliced'] = tf.slice(features['comment_padded'], [0,0], [-1, MAX_DOCUMENT_LENGTH])
features['comment_words'] = tf.pad(features['comment_sliced'], features['comment_padding'])
features['comment_words'] = tf.slice(features['comment_words'],[0,0],[-1,MAX_DOCUMENT_LENGTH])
features.pop('comment_padding')
features.pop('comment_padded')
features.pop('comment_sliced')
label = features.pop(LABEL_COLUMN)
return features, label
# Use prefix to create file path
file_path = '{}/{}*{}*'.format(INPUT_DIR, prefix, PATTERN)
# Create list of files that match pattern
file_list = tf.gfile.Glob(file_path)
# Create dataset from file list
dataset = (tf.data.TextLineDataset(file_list) # Read text file
.map(decode_csv)) # Transform each elem by applying decode_csv fn
tf.logging.info("...dataset.output_types={}".format(dataset.output_types))
tf.logging.info("...dataset.output_shapes={}".format(dataset.output_shapes))
if mode == tf.estimator.ModeKeys.TRAIN:
num_epochs = None # indefinitely
dataset = dataset.shuffle(buffer_size = 10 * batch_size)
else:
num_epochs = 1 # end-of-input after this
dataset = dataset.repeat(num_epochs).batch(batch_size)
return dataset.make_one_shot_iterator().get_next()
return _input_fn
然后在下面的函数中,我们可以引用我们在 decode_csv()
中创建的字段:
# Define feature columns
def get_wide_deep():
EMBEDDING_SIZE = 10
# Define column types
subreddit = tf.feature_column.categorical_column_with_vocabulary_list('subreddit', ['news', 'ireland', 'pics'])
comment_embeds = tf.feature_column.embedding_column(
categorical_column = tf.feature_column.categorical_column_with_vocabulary_file(
key='comment_words',
vocabulary_file='{}/vocab.csv-00000-of-00001'.format(INPUT_DIR),
vocabulary_size=100
),
dimension = EMBEDDING_SIZE
)
# Sparse columns are wide, have a linear relationship with the output
wide = [ subreddit ]
# Continuous columns are deep, have a complex relationship with the output
deep = [ comment_embeds ]
return wide, deep