Skip to content

Commit 77d1b58

Browse files
authored
Keras models support (#7)
* temp add * fix tests * update * addback * update * fit iris test case * follow comments
1 parent eabd7c7 commit 77d1b58

File tree

6 files changed

+97
-1
lines changed

6 files changed

+97
-1
lines changed

.travis.yml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,6 @@ language: python
1212
python:
1313
- 3.6
1414
- 3.7
15-
- 3.8-dev
1615

1716
install:
1817
- python setup.py -q install

setup.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222

2323
# What packages are required for this module to be executed?
2424
REQUIRED = [
25+
'tensorflow==2.0.0-alpha0'
2526
]
2627
SETUP_REQUIRED = [
2728
'pytest-runner'

sqlflow_models/__init__.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,2 @@
11
from ._version import __version__
2+
from .dnnclassifier import DNNClassifier

sqlflow_models/dnnclassifier.py

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
import tensorflow as tf
2+
3+
class DNNClassifier(tf.keras.Model):
4+
def __init__(self, feature_columns, hidden_units=[10,10], n_classes=2):
5+
"""DNNClassifier
6+
:param feature_columns: feature columns.
7+
:type feature_columns: list[tf.feature_column].
8+
:param hidden_units: number of hidden units.
9+
:type hidden_units: list[int].
10+
:param n_classes: List of hidden units per layer.
11+
:type n_classes: int.
12+
"""
13+
super(DNNClassifier, self).__init__()
14+
15+
# combines all the data as a dense tensor
16+
self.feature_layer = tf.keras.layers.DenseFeatures(feature_columns)
17+
self.hidden_layers = []
18+
for hidden_unit in hidden_units:
19+
self.hidden_layers.append(tf.keras.layers.Dense(hidden_unit))
20+
self.prediction_layer = tf.keras.layers.Dense(n_classes, activation='softmax')
21+
22+
def call(self, inputs):
23+
x = self.feature_layer(inputs)
24+
for hidden_layer in self.hidden_layers:
25+
x = hidden_layer(x)
26+
return self.prediction_layer(x)
27+
28+
def default_optimizer(self):
29+
"""Default optimizer name. Used in model.compile."""
30+
return tf.keras.optimizers.Adagrad(lr=0.1)
31+
32+
def default_loss(self):
33+
"""Default loss function. Used in model.compile."""
34+
return 'sparse_categorical_crossentropy'
35+
36+
def default_training_epochs(self):
37+
"""Default training epochs. Used in model.fit."""
38+
return 2
39+
40+
def prepare_prediction_column(self, prediction):
41+
"""Return the class label of highest probability."""
42+
return prediction.argmax(axis=-1)

tests/base.py

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
import unittest
2+
import tensorflow as tf
3+
4+
def train_input_fn(features, labels, batch_size=32):
5+
dataset = tf.data.Dataset.from_tensor_slices((dict(features), labels))
6+
dataset = dataset.shuffle(1000).repeat().batch(batch_size)
7+
return dataset
8+
9+
def eval_input_fn(features, labels, batch_size=32):
10+
dataset = tf.data.Dataset.from_tensor_slices((dict(features), labels))
11+
dataset = dataset.batch(batch_size)
12+
return dataset
13+
14+
class BaseTestCases:
15+
class BaseTest(object):
16+
def setUp(self):
17+
self.model, self.features, self.label = None, {}, None
18+
19+
def test_train_and_predict(self):
20+
self.setUp()
21+
22+
self.model.compile(optimizer=self.model.default_optimizer(),
23+
loss=self.model.default_loss(),
24+
metrics=["accuracy"])
25+
self.model.fit(train_input_fn(self.features, self.label),
26+
epochs=self.model.default_training_epochs(),
27+
steps_per_epoch=100, verbose=0)
28+
loss, acc = self.model.evaluate(eval_input_fn(self.features, self.label))
29+
print(loss, acc)
30+
assert(loss < 10)
31+
assert(acc > 0.3)

tests/test_dnnclassifier.py

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
import sqlflow_models
2+
from .base import BaseTestCases
3+
4+
import tensorflow as tf
5+
import unittest
6+
7+
8+
class TestDNNClassifier(BaseTestCases.BaseTest):
9+
def setUp(self):
10+
self.features = {"c1": [float(x) for x in range(100)],
11+
"c2": [float(x) for x in range(100)],
12+
"c3": [float(x) for x in range(100)],
13+
"c4": [float(x) for x in range(100)]}
14+
self.label = [0 for _ in range(50)] + [1 for _ in range(50)]
15+
feature_columns = [tf.feature_column.numeric_column(key) for key in
16+
self.features]
17+
self.model = sqlflow_models.DNNClassifier(feature_columns=feature_columns)
18+
19+
20+
if __name__ == '__main__':
21+
unittest.main()
22+

0 commit comments

Comments
 (0)