Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added Convolutional LSTM #8891

Merged
merged 31 commits into from Aug 7, 2017

Conversation

loliverhennigh
Copy link
Contributor

Added an implementation of convolutional lstms (https://arxiv.org/abs/1506.04214). Related to this issue #4536 .

@tensorflow-jenkins
Copy link
Collaborator

Can one of the admins verify this patch?

@yifeif yifeif requested a review from ebrevdo April 3, 2017 04:18
@yifeif yifeif added the stat:awaiting tensorflower Status - Awaiting response from tensorflower label Apr 3, 2017
@marcociccone
Copy link

marcociccone commented Apr 3, 2017

I think that if you want to use the cell with dynamic_rnn wrapper, this will not work because it expects a 3D tensor for the scan. Am I right?

@ebrevdo
Copy link
Contributor

ebrevdo commented Apr 3, 2017 via email

@marcociccone
Copy link

Thanks @ebrevdo, since when it is supported? I'm having an error with my implementation that the shape must be 3D so I'm asking. Do I need to specify any abstract method or something else?

I tag @carlthome because I think he's interested too

@ebrevdo
Copy link
Contributor

ebrevdo commented Apr 3, 2017 via email

@marcociccone
Copy link

It doesn't seem so, here we have a reshape that fails if I have more than 2 dimensions. Am I missing something? I can open an issue in case I'm right

else:
res = nn_ops.conv2d(array_ops.concat(axis=3, values=args), matrix, strides=[1, 1, 1, 1], padding='SAME')
if not bias:
return res
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's bad style to have multiple returns in the same function.

Rather do if bias: res += bias

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I cleaned this up a little bit however the function still has the 2 return statements. The reason I wrote it this way was because the _linear function written in tensorflow/contrib/rnn/python/ops/core_rnn_cell_impl.py has 2 return statements. I can definitely change it but it seemed more consistent to do it this way.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How unfortunate, but consistency 👍

# Parameters of gates are concatenated into one multiply for efficiency.
(c, h) = state

concat = _conv_linear([inputs, h], self._filter_size, self._num_features * 4, True)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If self._num_features is 1, will the gates be created? I think the minimum should be 4 here, no?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I do not believe this is a issue. The gates will still be created. In the tensorflow/contrib/rnn/python/kernel_tests/rnn_cell_test.py test I wrote, the filter size is set to 1 with no issues


@property
def output_size(self):
return self._shape
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't this include self._num_features?


@property
def state_size(self):
return core_rnn_cell.LSTMStateTuple(self._shape, self._shape)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't this include self._num_features?

@drpngx drpngx added stat:awaiting response Status - Awaiting response from author and removed stat:awaiting tensorflower Status - Awaiting response from tensorflower labels Apr 14, 2017
@bhack
Copy link
Contributor

bhack commented Apr 24, 2017

Any update on this review?

@carlthome
Copy link
Contributor

I don't think this works with tf.nn.dynamic_rnn.

@bhack
Copy link
Contributor

bhack commented Apr 28, 2017

@loliverhennigh Do you plan to come back again on this?

@loliverhennigh
Copy link
Contributor Author

I updated some of the issues mention above

@vrv
Copy link

vrv commented May 1, 2017

@carlthome @ebrevdo let us know what the next steps are!

@ebrevdo
Copy link
Contributor

ebrevdo commented May 2, 2017

Hi @loliverhennigh! Thanks for taking the time to sit down and implement this.

Have you seen sonnet's ConvLSTM module? They have a very nice API and implementation that is sort-of but not 100% identical to yours. Would you be interested in writing a ConvLSTM matching this API / impl?

Note also we've gotten rid of _checked_scope in favor of RNNCell subclassing tf.layers.Layer; so we no longer override call but instead have a "def call(self, inputs, state):"

@vrv
Copy link

vrv commented May 4, 2017

friendly ping for @loliverhennigh

@loliverhennigh
Copy link
Contributor Author

Oh cool, I had not seen sonnet yet. I could definitely rewrite my ConvLstm to match that one. I like that it has support for 1,2, and 3d convs.

@ebrevdo
Copy link
Contributor

ebrevdo commented May 5, 2017 via email

Copy link
Contributor

@ebrevdo ebrevdo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you add versions of the same tests where the batch size is not known and you feed the inputs and initial state via feed_dict to session.run? This should ensure the code works for batch size a Tensor.

@vrv
Copy link

vrv commented Jul 24, 2017

Ping for @loliverhennigh on the last comment about adding tests.

@vrv vrv added stat:awaiting response Status - Awaiting response from author and removed awaiting review Pull request awaiting review stat:awaiting tensorflower Status - Awaiting response from tensorflower labels Jul 24, 2017
@loliverhennigh
Copy link
Contributor Author

I think this fixes the variable batch size problem and also allows for variable image sizes. The kernel tests now reflect this. I think this might be all good now

Copy link
Contributor

@lukaszkaiser lukaszkaiser left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The code looks good to me, thanks! (One could remove the conv_dims or have just 1 class, but the current version looks consistent with our layers, so I don't have any strong opinion on that.)

@drpngx
Copy link
Contributor

drpngx commented Aug 5, 2017 via email

@drpngx
Copy link
Contributor

drpngx commented Aug 7, 2017

Jenkins, test this please.

@drpngx
Copy link
Contributor

drpngx commented Aug 7, 2017

The Linux build is transient, but there is a windows build error:

08:30:35      4>measuring_cost_estimator.obj : error LNK2019: unresolved external symbol "class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > __cdecl tensorflow::SanitizeThreadSuffix(class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >)" (?SanitizeThreadSuffix@tensorflow@@YA?AV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@V23@@Z) referenced in function "public: __cdecl tensorflow::grappler::MeasuringCostEstimator::MeasuringCostEstimator(class tensorflow::grappler::Cluster *,int,int)" (??0MeasuringCostEstimator@grappler@tensorflow@@QEAA@PEAVCluster@12@HH@Z) [C:\tf_jenkins\home\workspace\tensorflow-pr-win-cmake-py\cmake_build\pywrap_tensorflow_internal.vcxproj]
08:30:35      4>queue_runner.obj : error LNK2001: unresolved external symbol "class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > __cdecl tensorflow::SanitizeThreadSuffix(class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >)" (?SanitizeThreadSuffix@tensorflow@@YA?AV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@V23@@Z) [C:\tf_jenkins\home\workspace\tensorflow-pr-win-cmake-py\cmake_build\pywrap_tensorflow_internal.vcxproj]
08:30:35      4>single_machine.obj : error LNK2001: unresolved external symbol "class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > __cdecl tensorflow::SanitizeThreadSuffix(class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >)" (?SanitizeThreadSuffix@tensorflow@@YA?AV?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@V23@@Z) [C:\tf_jenkins\home\workspace\tensorflow-pr-win-cmake-py\cmake_build\pywrap_tensorflow_internal.vcxproj]
08:30:35      4>C:\tf_jenkins\home\workspace\tensorflow-pr-win-cmake-py\cmake_build\Release\pywrap_tensorflow_internal.dll : fatal error LNK1120: 1 unresolved externals [C:\tf_jenkins\home\workspace\tensorflow-pr-win-cmake-py\cmake_build\pywrap_tensorflow_internal.vcxproj]
08:30:35      4>Done Building Project "C:\tf_jenkins\home\workspace\tensorflow-pr-win-cmake-py\cmake_build\pywrap_tensorflow_internal.vcxproj" (default targets) -- FAILED.
08:30:35      1>Done Building Project "c:\tf_jenkins\home\workspace\tensorflow-pr-win-cmake-py\cmake_build\tf_python_build_pip_package.vcxproj" (default targets) -- FAILED.
08:30:35 

@ebrevdo
Copy link
Contributor

ebrevdo commented Aug 7, 2017 via email

@drpngx
Copy link
Contributor

drpngx commented Aug 7, 2017

Right. Merging.

@drpngx drpngx merged commit e9682dd into tensorflow:master Aug 7, 2017
ishay2b pushed a commit to ishay2b/tensorflow that referenced this pull request Aug 8, 2017
…assification

* commit '6e054dbd4b741d5b8fa8af93fdd7c9b74ae67ce0': (511 commits)
  Fix tensordot with list of ints as axes (tensorflow#11959)
  Fix segfault when recording raw allocation returns nullptr (tensorflow#12074)
  [OpenCL] Fix for //tensorflow/python/kernel_tests:image_ops_test (tensorflow#111) (tensorflow#12041)
  Removing visited_node hash table - fixing multinode shape mismatch issue (tensorflow#12044)
  [OpenCL] Fixes core_rnn_cell_tests (tensorflow#12076)
  Added Convolutional LSTM (tensorflow#8891)
  Update monitors_test.py (tensorflow#12062)
  fix a typo in tf.nn.separable_conv2d's doc (tensorflow#12067)
  Fix cmake builds: (tensorflow#12048)
  Fix typo in RELEASE.md (tensorflow#12064)
  Fix typo (tensorflow#12069)
  Handle case where init node is not present in the frozen graph.
  Fix typo in datasets docstring
  tfdbg: fix a bug in string representation of SparseTensors
  BUILD dependency cleanup in tensorflow/stream_executor/cuda
  BUILD dependency cleanups. Rename RecvTensorAsync method to GrpcRecvTensorAsync to fix shadowing of method in Worker with a different signature.
  [tpu:profiler] Dump gzipped json trace.
  Minor cleanup
  tf.nn.separable_conv2d now supports data_format. Avoid unnecessary transposes in tf.layers.separable_conv2d (and implicitly in tf.contrib.layers.separable_conv2d).
  Add an identity initializer that works with partitioned variables.
  ...
@lcnature
Copy link

lcnature commented Aug 16, 2017

Hi @loliverhennigh I am trying to use it together with dynamic_rnn but got some errors. May I understand the input_shape better? Say I want the input to be video of size 32x32, 3 channels for RGB. Each video clip has 10 frames. What exactly should I feed to the input_shape argument? And let's say the batch_size is 5, how should the size of the inputs be if it is used together with dynamic_rnn?
Thank you!

@loliverhennigh
Copy link
Contributor Author

Hey @Icnature, I wrote a little silly example of how to use the conv2dlstmcell with the dynamic_rnn stuff here
https://github.com/loliverhennigh/dynamic_rnn_conv_lstm/blob/master/mnist_deep.py#L57. To answer your question though, your input shape should be [32,32,3]. You can have your inputs be any shape that is supported by the dynamic rnn thing. In the example above the shape is [batch_size, seq_length, height, width, channels]. If you change time_major to True I think it will be [seq_length, batch_size, height, width, channels]. Hopefully that answers your question ok!

@lcnature
Copy link

Thanks @loliverhennigh ! I figured out my mistake. I was actually trying Conv1DLSTMcell. The kernel_shape should be a list instead of an integer.

@rayanelleuch
Copy link

rayanelleuch commented Oct 17, 2017

@loliverhennigh
I feel like it is little bit disturbing to not be able to choose the padding style, stride, activation function, bias, etc like tf.contrib.layers.conv2d .
Is there a specific reason for that?

@Linusnie
Copy link

Linusnie commented Nov 2, 2017

In the original paper they use peephole connections (i.e. the gates depend on the hidden state) but as far as I can tell these connections are not present in the implementation. Is this intentional? Might be worth it do mention in the documentation in that case.

@carlthome
Copy link
Contributor

@Linusnie for now you can use my implementation here instead. I find peepholes important, by the way.

@anjany
Copy link

anjany commented Nov 6, 2017

Hi @loliverhennigh!
Will I be able to use this for inputs with dynamic image shapes (consequently the cell shape would be changing too)?

I get a typical TypeError: int() argument must be a string or a number, not 'Tensor' for the code below. Am I doing something exceptionally wrong?

def _convlstm_layer(x):
	# x is shaped [batch_size, seq_len, _, _, 1]
	shape = [tf.shape(x)[2], tf.shape(x)[3], tf.shape(x)[4]]
        cell = tf.contrib.rnn.Conv2DLSTMCell(input_shape=shape,kernel_shape=[3,3], output_channels=8)
	(outputs, state) = tf.nn.dynamic_rnn(cell, x, time_major=False, dtype=tf.float32)
	return outputs

for shape in shapes:
if len(shape) not in [3,4,5]:
raise ValueError("Conv Linear expects 3D, 4D or 5D arguments: %s" % str(shapes))
if len(shape) != len(shapes[0]):

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You could just use shape_length instead of recalculating it again.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
cla: yes stat:awaiting response Status - Awaiting response from author
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet