mirror of
				https://github.com/pytorch/pytorch.git
				synced 2025-10-30 19:54:53 +08:00 
			
		
		
		
	Compare commits
	
		
			23 Commits
		
	
	
		
			ciflow/tru
			...
			v0.4.0
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
| 3749c581b7 | |||
| 200fb22b22 | |||
| 86b2165ab8 | |||
| 07091ad7dc | |||
| 92b137a9ed | |||
| ce0f350393 | |||
| 77e8c92ab9 | |||
| 46c534a14e | |||
| 58ed43d6e4 | |||
| 5f93a2b14c | |||
| 10175ed4f2 | |||
| 307db03fac | |||
| 98822f3753 | |||
| dd5a319055 | |||
| 9b90c66af8 | |||
| 7cba734a59 | |||
| 38aaa6354f | |||
| 8b767d2b0f | |||
| 068fb53fd2 | |||
| 06caf5d76f | |||
| 951cdc2b22 | |||
| eaba629943 | |||
| 33c2dc99cf | 
							
								
								
									
										2
									
								
								.gitmodules
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										2
									
								
								.gitmodules
									
									
									
									
										vendored
									
									
								
							| @ -22,7 +22,7 @@ | ||||
| 	url = https://github.com/NVlabs/cub.git | ||||
| [submodule "third_party/eigen"] | ||||
| 	path = third_party/eigen | ||||
| 	url = https://github.com/RLovelett/eigen.git | ||||
| 	url = https://github.com/eigenteam/eigen-git-mirror.git | ||||
| [submodule "third_party/googletest"] | ||||
| 	path = third_party/googletest | ||||
| 	url = https://github.com/google/googletest.git | ||||
|  | ||||
| @ -123,11 +123,6 @@ function(filter_list output input) | ||||
| endfunction() | ||||
|  | ||||
|  | ||||
| IF ($ENV{TH_BINARY_BUILD}) | ||||
|   MESSAGE(STATUS "TH_BINARY_BUILD detected. Statically linking libstdc++") | ||||
|   SET(CMAKE_CXX_FLAGS "-static-libstdc++ ${CMAKE_CXX_FLAGS}") | ||||
| ENDIF() | ||||
|  | ||||
| # Can be compiled standalone | ||||
| IF(NOT AT_INSTALL_BIN_DIR OR NOT AT_INSTALL_LIB_DIR OR NOT AT_INSTALL_INCLUDE_DIR OR NOT AT_INSTALL_SHARE_DIR) | ||||
|   SET(AT_INSTALL_BIN_DIR "bin" CACHE PATH "AT install binary subdirectory") | ||||
| @ -332,12 +327,55 @@ ENDIF() | ||||
| TARGET_LINK_LIBRARIES(ATen cpuinfo) | ||||
|  | ||||
| IF(CUDA_FOUND) | ||||
|   TARGET_LINK_LIBRARIES(ATen | ||||
|     ${CUDA_LIBRARIES} | ||||
|     ${CUDA_cusparse_LIBRARY} | ||||
|     ${CUDA_curand_LIBRARY}) | ||||
|   CUDA_ADD_CUBLAS_TO_TARGET(ATen) | ||||
|   CUDA_ADD_CUFFT_TO_TARGET(ATen) | ||||
|   IF ($ENV{ATEN_STATIC_CUDA}) | ||||
|     # CuFFT has a complicated static story (especially around CUDA < 9) because it has device callback support | ||||
|     # we first have to build a fake lib that links with no device callbacks, | ||||
|     # and then we link against this object file. | ||||
|     # This was recommended by the CuFFT team at NVIDIA | ||||
|  | ||||
|     # build fake CuFFT lib in build dir | ||||
|     EXECUTE_PROCESS(COMMAND touch ${CMAKE_CURRENT_BINARY_DIR}/empty_file.cc) | ||||
|     if(${CUDA_VERSION_MAJOR} EQUAL "8") | ||||
|       SET(CUFFT_FAKELINK_OPTIONS | ||||
| 	--generate-code arch=compute_35,code=sm_35 | ||||
| 	--generate-code arch=compute_50,code=sm_50 | ||||
| 	--generate-code arch=compute_60,code=sm_60) | ||||
|     elseif(${CUDA_VERSION_MAJOR} EQUAL "9") | ||||
|       SET(CUFFT_FAKELINK_OPTIONS | ||||
| 	--generate-code arch=compute_35,code=sm_35 | ||||
| 	--generate-code arch=compute_50,code=sm_50 | ||||
| 	--generate-code arch=compute_60,code=sm_60 | ||||
| 	--generate-code arch=compute_70,code=sm_70) | ||||
|     else() | ||||
|       MESSAGE(FATAL_ERROR "Unhandled major cuda version ${CUDA_VERSION_MAJOR}") | ||||
|     endif() | ||||
|     ADD_CUSTOM_COMMAND( | ||||
|       OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/cufft_static_library.a | ||||
|       COMMAND "${CUDA_TOOLKIT_ROOT_DIR}/bin/nvcc" -o ${CMAKE_CURRENT_BINARY_DIR}/cufft_static_library.a -Xcompiler -fPIC | ||||
|       ${CUFFT_FAKELINK_OPTIONS} | ||||
|       --device-link ${CMAKE_CURRENT_BINARY_DIR}/empty_file.cc -lcufft_static -lculibos | ||||
|       ) | ||||
|     ADD_CUSTOM_TARGET(FAKELINKED_CUFFT_TARGET DEPENDS ${CMAKE_CURRENT_BINARY_DIR}/cufft_static_library.a) | ||||
|     add_library(FAKELINKED_CUFFT STATIC IMPORTED GLOBAL) | ||||
|     add_dependencies(FAKELINKED_CUFFT FAKELINKED_CUFFT_TARGET) | ||||
|     set_target_properties(FAKELINKED_CUFFT PROPERTIES IMPORTED_LOCATION ${CMAKE_CURRENT_BINARY_DIR}/cufft_static_library.a) | ||||
|  | ||||
|     TARGET_LINK_LIBRARIES(ATen | ||||
|       ${CUDA_LIBRARIES} | ||||
|       ${CUDA_TOOLKIT_ROOT_DIR}/lib64/libcusparse_static.a | ||||
|       ${CUDA_TOOLKIT_ROOT_DIR}/lib64/libcurand_static.a | ||||
|       ${CUDA_TOOLKIT_ROOT_DIR}/lib64/libcublas_static.a | ||||
|       FAKELINKED_CUFFT | ||||
|       ${CUDA_TOOLKIT_ROOT_DIR}/lib64/libcufft_static.a | ||||
|       ) | ||||
|   ELSE() | ||||
|     TARGET_LINK_LIBRARIES(ATen | ||||
|       ${CUDA_LIBRARIES} | ||||
|       ${CUDA_cusparse_LIBRARY} | ||||
|       ${CUDA_curand_LIBRARY}) | ||||
|     CUDA_ADD_CUBLAS_TO_TARGET(ATen) | ||||
|     CUDA_ADD_CUFFT_TO_TARGET(ATen) | ||||
|   ENDIF() | ||||
|  | ||||
|   if(CUDNN_FOUND) | ||||
|     target_link_libraries(ATen ${CUDNN_LIBRARIES}) | ||||
|  | ||||
| @ -3,7 +3,6 @@ | ||||
| #include "ATen/ExpandUtils.h" | ||||
| #include "ATen/NativeFunctions.h" | ||||
| #include "ATen/WrapDimUtils.h" | ||||
| #include "cpu/ReduceOpsKernel.h" | ||||
|  | ||||
| #include <algorithm> | ||||
| #include <functional> | ||||
| @ -92,11 +91,6 @@ Tensor sum(const Tensor &self) { | ||||
| } | ||||
|  | ||||
| Tensor _sum_cpu(const Tensor& self) { | ||||
|   if (self.is_contiguous()) { | ||||
|     Tensor result = self.type().tensor({}); | ||||
|     sum_kernel(result, self, at::nullopt); | ||||
|     return result; | ||||
|   } | ||||
|   return self._sumall(); | ||||
| } | ||||
|  | ||||
| @ -113,11 +107,6 @@ Tensor prod(const Tensor &self) { | ||||
| } | ||||
|  | ||||
| Tensor _prod_cpu(const Tensor &self) { | ||||
|   if (self.is_contiguous()) { | ||||
|     Tensor result = self.type().tensor({}); | ||||
|     prod_kernel(result, self, at::nullopt); | ||||
|     return result; | ||||
|   } | ||||
|   return self._prodall(); | ||||
| } | ||||
|  | ||||
| @ -180,12 +169,6 @@ Tensor &_sum_out_cpu(Tensor &result, const Tensor &self, int64_t dim_, | ||||
|   int64_t dim = maybe_wrap_dim(dim_, self.dim()); | ||||
|   if (_dimreduce_return_trivial(result, self, 0)) | ||||
|     return result; | ||||
|   if (self.is_contiguous() && result.is_contiguous()) { | ||||
|     _dimreduce_setup(result, self, dim); | ||||
|     sum_kernel(result, self, dim); | ||||
|     if (!keepdim) result.squeeze_(dim); | ||||
|     return result; | ||||
|   } | ||||
|   return at::_th_sum_out(result, self, dim, keepdim); | ||||
| } | ||||
|  | ||||
| @ -214,12 +197,6 @@ Tensor &_prod_out_cpu(Tensor &result, const Tensor &self, int64_t dim_, | ||||
|   int64_t dim = maybe_wrap_dim(dim_, self.dim()); | ||||
|   if (_dimreduce_return_trivial(result, self, 1)) | ||||
|     return result; | ||||
|   if (self.is_contiguous() && result.is_contiguous()) { | ||||
|     _dimreduce_setup(result, self, dim); | ||||
|     prod_kernel(result, self, dim); | ||||
|     if (!keepdim) result.squeeze_(dim); | ||||
|     return result; | ||||
|   } | ||||
|   return at::_th_prod_out(result, self, dim, keepdim); | ||||
| } | ||||
|  | ||||
|  | ||||
| @ -1,154 +0,0 @@ | ||||
| #include "ATen/native/cpu/ReduceOpsKernel.h" | ||||
|  | ||||
| #include <numeric> | ||||
|  | ||||
| #include "ATen/Dispatch.h" | ||||
| #include "ATen/Parallel.h" | ||||
| #include "ATen/optional.h" | ||||
| #include "ATen/cpu/vec256/vec256.h" | ||||
|  | ||||
| namespace at { namespace native { namespace { | ||||
|  | ||||
| using namespace vec256; | ||||
|  | ||||
| static inline int64_t round_down(int64_t a, int64_t m) { | ||||
|   return a - (a % m); | ||||
| } | ||||
|  | ||||
| template<typename F> | ||||
| static void parallel_for(int64_t end, int64_t step, bool parallelize, F func) { | ||||
|   if (parallelize) { | ||||
|     tbb::parallel_for<int64_t>(0, end, step, func); | ||||
|   } else { | ||||
|     for (int64_t i = 0; i != end; i += step) { | ||||
|       func(i); | ||||
|     } | ||||
|   } | ||||
| } | ||||
|  | ||||
| static tbb::affinity_partitioner ap; | ||||
|  | ||||
| // Vectorized reduction defined by reduce operation `Op` with identity `ident`. | ||||
| // The reduction is built on top of reduce128, which reduces down a column | ||||
| // 128 bytes wide (WIDTH scalar elements). The width of 128 bytes is chosen | ||||
| // because of the "adjacent cache line prefetch" behavior on x86 CPUs. | ||||
| template<typename scalar_t, template <class> class Op, int ident> | ||||
| struct Reduction { | ||||
|   // reduction width in number of scalar elements | ||||
|   static constexpr int WIDTH = 128 / sizeof(scalar_t); | ||||
|  | ||||
|   using Vec = Vec256<scalar_t>; | ||||
|   using Reduce = Op<Vec>; | ||||
|   using ReduceScalar = Op<scalar_t>; | ||||
|  | ||||
|   static void apply(Tensor& res, const Tensor& self, at::optional<int64_t> dim) { | ||||
|     internal::init_tbb_num_threads(); | ||||
|  | ||||
|     auto out = res.data<scalar_t>(); | ||||
|     auto data = self.data<scalar_t>(); | ||||
|     auto numel = self.numel(); | ||||
|     if (!dim.has_value()) { | ||||
|       *out = reduce_all(data, numel); | ||||
|       return; | ||||
|     } | ||||
|  | ||||
|     int64_t n = self.size(*dim); | ||||
|     int64_t stride = self.stride(*dim); | ||||
|     int64_t batch = numel / (n * stride); | ||||
|     bool paralellize = batch * n > internal::TBB_GRAIN_SIZE; | ||||
|     parallel_for(batch, 1, paralellize, [=](int64_t b) { | ||||
|       if (stride == 1) { | ||||
|         out[b] = reduce_all(&data[b * n], n); | ||||
|       } else { | ||||
|         reduce2d(&data[b * n * stride], &out[b * stride], n, stride, stride); | ||||
|       } | ||||
|     }); | ||||
|   } | ||||
|  | ||||
|   static scalar_t reduce_all(const scalar_t* data, int64_t size) { | ||||
|     int64_t k = size / WIDTH; | ||||
|  | ||||
|     scalar_t sum; | ||||
|     if (size > internal::TBB_GRAIN_SIZE) { | ||||
|       sum = tbb::parallel_reduce( | ||||
|           tbb::blocked_range<int64_t>(0, k, internal::TBB_GRAIN_SIZE / WIDTH), | ||||
|           scalar_t(ident), | ||||
|           [=](const tbb::blocked_range<int64_t>& r, scalar_t init) { | ||||
|             scalar_t buf[WIDTH]; | ||||
|             reduce128(&data[r.begin() * WIDTH], buf, r.end() - r.begin(), WIDTH); | ||||
|             return std::accumulate(buf, buf + WIDTH, init, ReduceScalar()); | ||||
|           }, | ||||
|           ReduceScalar(), | ||||
|           ap); | ||||
|     } else { | ||||
|       scalar_t buf[WIDTH]; | ||||
|       reduce128(data, buf, k, WIDTH); | ||||
|       sum = std::accumulate(buf, buf + WIDTH, scalar_t(ident), ReduceScalar()); | ||||
|     } | ||||
|  | ||||
|     for (int i = k * WIDTH; i != size; i++) { | ||||
|       sum = ReduceScalar()(sum, data[i]); | ||||
|     } | ||||
|     return sum; | ||||
|   } | ||||
|  | ||||
|   // Reduce down a column of WIDTH elements (128 bytes) with the given number | ||||
|   // of rows. Stores the results in out[0 ... WIDTH-1]. | ||||
|   static void reduce128(const scalar_t* data, scalar_t* out, int64_t rows, int64_t stride) { | ||||
|     Vec acc[4] = {ident, ident, ident, ident};  // 128 bytes (two cache lines) | ||||
|     static_assert(sizeof(acc) == 128, "accumulator should be 128 bytes"); | ||||
|     for (int64_t row = 0; row != rows; row++) { | ||||
|       for (int j = 0; j != 4; j++) { | ||||
|         auto val = Vec::s_load(&data[row * stride + j * Vec::size]); | ||||
|         acc[j] = Reduce()(acc[j], val); | ||||
|       } | ||||
|     } | ||||
|     for (int j = 0; j != 4; j++) { | ||||
|       acc[j].store(&out[j * Vec::size]); | ||||
|     } | ||||
|   } | ||||
|  | ||||
|   // Reduce a 2d matrix down each column. Stores the results in out[0 ... cols-1] | ||||
|   static void reduce2d(const scalar_t* data, scalar_t* out, int64_t rows, int64_t cols, int64_t stride) { | ||||
|     int64_t cols_rounded = round_down(cols, WIDTH); | ||||
|     bool paralellize = cols * rows > internal::TBB_GRAIN_SIZE; | ||||
|     parallel_for(cols_rounded, WIDTH, paralellize, [=](int64_t col) { | ||||
|       reduce128(&data[col], &out[col], rows, stride); | ||||
|     }); | ||||
|  | ||||
|     if (cols_rounded != cols) { | ||||
|       scalar_t buf[WIDTH]; | ||||
|       for (int64_t j = 0; j != cols - cols_rounded; j++) { | ||||
|         buf[j] = ident; | ||||
|       } | ||||
|       for (int64_t row = 0; row != rows; row++) { | ||||
|         for (int64_t j = 0; j != cols - cols_rounded; j++) { | ||||
|           auto val = data[row * stride + j + cols_rounded]; | ||||
|           buf[j] = ReduceScalar()(buf[j], val); | ||||
|         } | ||||
|       } | ||||
|       for (int64_t j = 0; j != cols - cols_rounded; j++) { | ||||
|         out[j + cols_rounded] = buf[j]; | ||||
|       } | ||||
|     } | ||||
|   } | ||||
| }; | ||||
|  | ||||
| static void sum_kernel_impl(Tensor& result, const Tensor& self, at::optional<int64_t> dim) { | ||||
|   AT_DISPATCH_ALL_TYPES(self.type(), "sum", [&] { | ||||
|     Reduction<scalar_t, std::plus, 0>::apply(result, self, dim); | ||||
|   }); | ||||
| } | ||||
|  | ||||
| static void prod_kernel_impl(Tensor& result, const Tensor& self, at::optional<int64_t> dim) { | ||||
|   AT_DISPATCH_ALL_TYPES(self.type(), "prod", [&] { | ||||
|     Reduction<scalar_t, std::multiplies, 1>::apply(result, self, dim); | ||||
|   }); | ||||
| } | ||||
|  | ||||
| }  // anonymous namespace | ||||
|  | ||||
| REGISTER_DISPATCH(sum_kernel, &sum_kernel_impl); | ||||
| REGISTER_DISPATCH(prod_kernel, &prod_kernel_impl); | ||||
|  | ||||
| }}  // namespace at::native | ||||
| @ -1,16 +0,0 @@ | ||||
| #pragma once | ||||
|  | ||||
| #include <ATen/ATen.h> | ||||
| #include <ATen/optional.h> | ||||
| #include "CapabilityDispatch.h" | ||||
|  | ||||
| namespace at { | ||||
| namespace native { | ||||
|  | ||||
| using reduce_fn = void(*)(Tensor &, const Tensor &, at::optional<int64_t>); | ||||
|  | ||||
| extern DispatchStub<reduce_fn> sum_kernel; | ||||
| extern DispatchStub<reduce_fn> prod_kernel; | ||||
|  | ||||
| } | ||||
| } | ||||
| @ -392,6 +392,9 @@ THCTensor_(median)(THCState *state, | ||||
|   THCTensor *newValues = THCTensor_(newNarrow)(state, sorted, dimension, k, 1); | ||||
|   THCudaLongTensor *newIndices = THCudaLongTensor_newNarrow(state, sorted_indices, dimension, k, 1); | ||||
|  | ||||
|   THCTensor_(free)(state, sorted); | ||||
|   THCudaLongTensor_free(state, sorted_indices); | ||||
|  | ||||
|   if (!keepdim) { | ||||
|     THCTensor_(squeeze1d)(state, newValues, newValues, dimension); | ||||
|     THCudaLongTensor_squeeze1d(state, newIndices, newIndices, dimension); | ||||
|  | ||||
| @ -11,6 +11,8 @@ Automatic differentiation package - torch.autograd | ||||
|  | ||||
| .. autofunction:: grad | ||||
|  | ||||
| .. _locally-disable-grad: | ||||
|  | ||||
| Locally disabling gradient computation | ||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
|  | ||||
| @ -1,56 +0,0 @@ | ||||
| .. currentmodule:: torch | ||||
|  | ||||
| .. _device-doc: | ||||
|  | ||||
| torch.device | ||||
| =================================== | ||||
|  | ||||
| A :class:`torch.device` is an object representing the device on which a :class:`torch.Tensor` is | ||||
| or will be allocated. | ||||
|  | ||||
| The :class:`torch.device` contains a device type (``'cpu'`` or ``'cuda'``) and optional device ordinal for the | ||||
| device type.  If the device ordinal is not present, this represents the current device for the device type; | ||||
| e.g. a :class:`torch.Tensor` constructed with device ``'cuda'`` is equivalent to ``'cuda:X'`` where X is the result of | ||||
| :func:`torch.cuda.current_device()`. | ||||
|  | ||||
| A :class:`torch.Tensor`'s device can be accessed via the :attr:`Tensor.device` property. | ||||
|  | ||||
| A :class:`torch.device` can be constructed via a string or via a string and device ordinal | ||||
|  | ||||
| Via a string: | ||||
| :: | ||||
|  | ||||
|     >>> torch.device('cuda:0') | ||||
|     device(type='cuda', index=0) | ||||
|  | ||||
|     >>> torch.device('cpu') | ||||
|     device(type='cpu') | ||||
|  | ||||
|     >>> torch.device('cuda')  # current cuda device | ||||
|     device(type='cuda') | ||||
|  | ||||
| Via a string and device ordinal: | ||||
|  | ||||
| :: | ||||
|  | ||||
|     >>> torch.device('cuda', 0) | ||||
|     device(type='cuda', index=0) | ||||
|  | ||||
|     >>> torch.device('cpu', 0) | ||||
|     device(type='cpu', index=0) | ||||
|  | ||||
| .. note:: | ||||
|    For legacy reasons, a device can be constructed via a single device ordinal, which is treated | ||||
|    as a cuda device.  This matches :meth:`Tensor.get_device`, which returns an ordinal for cuda | ||||
|    tensors and is not supported for cpu tensors. | ||||
|  | ||||
|    >>> torch.device(1) | ||||
|    device(type='cuda', index=1) | ||||
|  | ||||
| .. note:: | ||||
|    Methods which take a device will generally accept a (properly formatted) string | ||||
|    or (legacy) integer device ordinal, i.e. the following are all equivalent: | ||||
|  | ||||
|    >>> torch.randn((2,3), device=torch.device('cuda:1')) | ||||
|    >>> torch.randn((2,3), device='cuda:1') | ||||
|    >>> torch.randn((2,3), device=1)  # legacy | ||||
| @ -24,7 +24,9 @@ PyTorch is an optimized tensor library for deep learning using GPUs and CPUs. | ||||
|  | ||||
|    torch | ||||
|    tensors | ||||
|    tensor_attributes | ||||
|    sparse | ||||
|    cuda | ||||
|    storage | ||||
|    nn | ||||
|    optim | ||||
| @ -32,9 +34,6 @@ PyTorch is an optimized tensor library for deep learning using GPUs and CPUs. | ||||
|    torch.distributions <distributions> | ||||
|    torch.multiprocessing <multiprocessing> | ||||
|    torch.distributed <distributed> | ||||
|    torch.legacy <legacy> | ||||
|    cuda | ||||
|    device | ||||
|    bottleneck | ||||
|    checkpoint | ||||
|    cpp_extension | ||||
| @ -42,6 +41,7 @@ PyTorch is an optimized tensor library for deep learning using GPUs and CPUs. | ||||
|    ffi | ||||
|    model_zoo | ||||
|    onnx | ||||
|    torch.legacy <legacy> | ||||
|  | ||||
| .. toctree:: | ||||
|    :glob: | ||||
|  | ||||
| @ -19,17 +19,17 @@ Two tensors are "broadcastable" if the following rules hold: | ||||
|  | ||||
| For Example:: | ||||
|  | ||||
|     >>> x=torch.FloatTensor(5,7,3) | ||||
|     >>> y=torch.FloatTensor(5,7,3) | ||||
|     >>> x=torch.empty(5,7,3) | ||||
|     >>> y=torch.empty(5,7,3) | ||||
|     # same shapes are always broadcastable (i.e. the above rules always hold) | ||||
|  | ||||
|     >>> x=torch.FloatTensor() | ||||
|     >>> y=torch.FloatTensor(2,2) | ||||
|     >>> x=torch.empty((0,)) | ||||
|     >>> y=torch.empty(2,2) | ||||
|     # x and y are not broadcastable, because x does not have at least 1 dimension | ||||
|  | ||||
|     # can line up trailing dimensions | ||||
|     >>> x=torch.FloatTensor(5,3,4,1) | ||||
|     >>> y=torch.FloatTensor(  3,1,1) | ||||
|     >>> x=torch.empty(5,3,4,1) | ||||
|     >>> y=torch.empty(  3,1,1) | ||||
|     # x and y are broadcastable. | ||||
|     # 1st trailing dimension: both have size 1 | ||||
|     # 2nd trailing dimension: y has size 1 | ||||
| @ -37,8 +37,8 @@ For Example:: | ||||
|     # 4th trailing dimension: y dimension doesn't exist | ||||
|  | ||||
|     # but: | ||||
|     >>> x=torch.FloatTensor(5,2,4,1) | ||||
|     >>> y=torch.FloatTensor(  3,1,1) | ||||
|     >>> x=torch.empty(5,2,4,1) | ||||
|     >>> y=torch.empty(  3,1,1) | ||||
|     # x and y are not broadcastable, because in the 3rd trailing dimension 2 != 3 | ||||
|  | ||||
| If two tensors :attr:`x`, :attr:`y` are "broadcastable", the resulting tensor size | ||||
| @ -52,19 +52,19 @@ is calculated as follows: | ||||
| For Example:: | ||||
|  | ||||
|     # can line up trailing dimensions to make reading easier | ||||
|     >>> x=torch.FloatTensor(5,1,4,1) | ||||
|     >>> y=torch.FloatTensor(  3,1,1) | ||||
|     >>> x=torch.empty(5,1,4,1) | ||||
|     >>> y=torch.empty(  3,1,1) | ||||
|     >>> (x+y).size() | ||||
|     torch.Size([5, 3, 4, 1]) | ||||
|  | ||||
|     # but not necessary: | ||||
|     >>> x=torch.FloatTensor(1) | ||||
|     >>> y=torch.FloatTensor(3,1,7) | ||||
|     >>> x=torch.empty(1) | ||||
|     >>> y=torch.empty(3,1,7) | ||||
|     >>> (x+y).size() | ||||
|     torch.Size([3, 1, 7]) | ||||
|  | ||||
|     >>> x=torch.FloatTensor(5,2,4,1) | ||||
|     >>> y=torch.FloatTensor(3,1,1) | ||||
|     >>> x=torch.empty(5,2,4,1) | ||||
|     >>> y=torch.empty(3,1,1) | ||||
|     >>> (x+y).size() | ||||
|     RuntimeError: The size of tensor a (2) must match the size of tensor b (3) at non-singleton dimension 1 | ||||
|  | ||||
| @ -75,14 +75,14 @@ as a result of the broadcast. | ||||
|  | ||||
| For Example:: | ||||
|  | ||||
|     >>> x=torch.FloatTensor(5,3,4,1) | ||||
|     >>> y=torch.FloatTensor(3,1,1) | ||||
|     >>> x=torch.empty(5,3,4,1) | ||||
|     >>> y=torch.empty(3,1,1) | ||||
|     >>> (x.add_(y)).size() | ||||
|     torch.Size([5, 3, 4, 1]) | ||||
|  | ||||
|     # but: | ||||
|     >>> x=torch.FloatTensor(1,3,1) | ||||
|     >>> y=torch.FloatTensor(3,1,7) | ||||
|     >>> x=torch.empty(1,3,1) | ||||
|     >>> y=torch.empty(3,1,7) | ||||
|     >>> (x.add_(y)).size() | ||||
|     RuntimeError: The expanded size of the tensor (1) must match the existing size (7) at non-singleton dimension 2. | ||||
|  | ||||
|  | ||||
| @ -12,35 +12,47 @@ However, once a tensor is allocated, you can do operations on it irrespective | ||||
| of the selected device, and the results will be always placed in on the same | ||||
| device as the tensor. | ||||
|  | ||||
| Cross-GPU operations are not allowed by default, with the only exception of | ||||
| :meth:`~torch.Tensor.copy_`. Unless you enable peer-to-peer memory access, any | ||||
| attempts to launch ops on tensors spread across different devices will raise an | ||||
| error. | ||||
| Cross-GPU operations are not allowed by default, with the exception of | ||||
| :meth:`~torch.Tensor.copy_` and other methods with copy-like functionality | ||||
| such as :meth:`~torch.Tensor.to` and :meth:`~torch.Tensor.cuda`. | ||||
| Unless you enable peer-to-peer memory access, any attempts to launch ops on | ||||
| tensors spread across different devices will raise an error. | ||||
|  | ||||
| Below you can find a small example showcasing this:: | ||||
|  | ||||
|     x = torch.cuda.FloatTensor(1) | ||||
|     # x.get_device() == 0 | ||||
|     y = torch.FloatTensor(1).cuda() | ||||
|     # y.get_device() == 0 | ||||
|     cuda = torch.device('cuda')     # Default CUDA device | ||||
|     cuda0 = torch.device('cuda:0') | ||||
|     cuda2 = torch.device('cuda:2')  # GPU 2 (these are 0-indexed) | ||||
|  | ||||
|     x = torch.tensor([1., 2.], device=cuda0) | ||||
|     # x.device is device(type='cuda', index=0) | ||||
|     y = torch.tensor([1., 2.]).cuda() | ||||
|     # y.device is device(type='cuda', index=0) | ||||
|  | ||||
|     with torch.cuda.device(1): | ||||
|         # allocates a tensor on GPU 1 | ||||
|         a = torch.cuda.FloatTensor(1) | ||||
|         a = torch.tensor([1., 2.], device=cuda) | ||||
|  | ||||
|         # transfers a tensor from CPU to GPU 1 | ||||
|         b = torch.FloatTensor(1).cuda() | ||||
|         # a.get_device() == b.get_device() == 1 | ||||
|         b = torch.tensor([1., 2.]).cuda() | ||||
|         # a.device and b.device are device(type='cuda', index=1) | ||||
|  | ||||
|         # You can also use ``Tensor.to`` to transfer a tensor: | ||||
|         b2 = torch.tensor([1., 2.]).to(device=cuda) | ||||
|         # b.device and b2.device are device(type='cuda', index=1) | ||||
|  | ||||
|         c = a + b | ||||
|         # c.get_device() == 1 | ||||
|         # c.device is device(type='cuda', index=1) | ||||
|  | ||||
|         z = x + y | ||||
|         # z.get_device() == 0 | ||||
|         # z.device is device(type='cuda', index=0) | ||||
|  | ||||
|         # even within a context, you can give a GPU id to the .cuda call | ||||
|         d = torch.randn(2).cuda(2) | ||||
|         # d.get_device() == 2 | ||||
|         # even within a context, you can specify the device | ||||
|         # (or give a GPU index to the .cuda call) | ||||
|         d = torch.randn(2, device=cuda2) | ||||
|         e = torch.randn(2).to(cuda2) | ||||
|         f = torch.randn(2).cuda(cuda2) | ||||
|         # d.device, e.device, and f.device are all device(type='cuda', index=2) | ||||
|  | ||||
| Asynchronous execution | ||||
| ---------------------- | ||||
| @ -79,8 +91,9 @@ relative order, unless explicit synchronization functions (such as | ||||
| :meth:`~torch.cuda.synchronize` or :meth:`~torch.cuda.Stream.wait_stream`) are | ||||
| used.  For example, the following code is incorrect:: | ||||
|  | ||||
|     cuda = torch.device('cuda') | ||||
|     s = torch.cuda.stream()  # Create a new stream. | ||||
|     A = torch.cuda.FloatTensor(100, 100).normal_(0.0, 1.0) | ||||
|     A = torch.empty((100, 100), device=cuda).normal_(0.0, 1.0) | ||||
|     with torch.cuda.stream(s): | ||||
|         # sum() may start execution before normal_() finishes! | ||||
|         B = torch.sum(A) | ||||
| @ -122,8 +135,10 @@ the initial hidden state of a recurrent neural network. | ||||
| The first step is to determine whether the GPU should be used or not. A common | ||||
| pattern is to use Python's ``argparse`` module to read in user arguments, and | ||||
| have a flag that can be used to disable CUDA, in combination with | ||||
| :meth:`~torch.cuda.is_available`. In the following, ``args.cuda`` results in a | ||||
| flag that can be used to cast tensors and modules to CUDA if desired:: | ||||
| :meth:`~torch.cuda.is_available`. In the following, ``args.device`` results in a | ||||
| :class:`torch.device` object that can be used to move tensors to CPU or CUDA. | ||||
|  | ||||
| :: | ||||
|  | ||||
|     import argparse | ||||
|     import torch | ||||
| @ -132,29 +147,35 @@ flag that can be used to cast tensors and modules to CUDA if desired:: | ||||
|     parser.add_argument('--disable-cuda', action='store_true', | ||||
|                         help='Disable CUDA') | ||||
|     args = parser.parse_args() | ||||
|     args.cuda = not args.disable_cuda and torch.cuda.is_available() | ||||
|     args.device = None | ||||
|     if not args.disable_cuda and torch.cuda.is_available(): | ||||
|         args.device = torch.device('cuda') | ||||
|     else: | ||||
|         args.device = torch.device('cpu') | ||||
|  | ||||
| If modules or tensors need to be sent to the GPU, ``args.cuda`` can be used as | ||||
| follows:: | ||||
| Now that we have ``args.device``, we can use it to create a Tensor on the | ||||
| desired device. | ||||
|  | ||||
|     x = torch.Tensor(8, 42) | ||||
|     net = Network() | ||||
|     if args.cuda: | ||||
|       x = x.cuda() | ||||
|       net.cuda() | ||||
| :: | ||||
|  | ||||
| When creating tensors, an alternative to the if statement is to have a default | ||||
| datatype defined, and cast all tensors using that. An example when using a | ||||
| dataloader would be as follows:: | ||||
|     x = torch.empty((8, 42), device=args.device) | ||||
|     net = Network().to(device=args.device) | ||||
|  | ||||
|     dtype = torch.cuda.FloatTensor | ||||
| This can be used in a number of cases to produce device agnostic code. Below | ||||
| is an example when using a dataloader: | ||||
|  | ||||
| :: | ||||
|  | ||||
|     cuda0 = torch.device('cuda:0')  # CUDA GPU 0 | ||||
|     for i, x in enumerate(train_loader): | ||||
|         x = Variable(x.type(dtype)) | ||||
|         x = x.to(cuda0) | ||||
|  | ||||
| When working with multiple GPUs on a system, you can use the | ||||
| ``CUDA_VISIBLE_DEVICES`` environment flag to manage which GPUs are available to | ||||
| PyTorch. As mentioned above, to manually control which GPU a tensor is created | ||||
| on, the best practice is to use a :any:`torch.cuda.device` context manager:: | ||||
| on, the best practice is to use a :any:`torch.cuda.device` context manager. | ||||
|  | ||||
| :: | ||||
|  | ||||
|     print("Outside device is 0")  # On device 0 (default in most scenarios) | ||||
|     with torch.cuda.device(1): | ||||
| @ -162,29 +183,52 @@ on, the best practice is to use a :any:`torch.cuda.device` context manager:: | ||||
|     print("Outside device is still 0")  # On device 0 | ||||
|  | ||||
| If you have a tensor and would like to create a new tensor of the same type on | ||||
| the same device, then you can use the :meth:`~torch.Tensor.new` method, which | ||||
| acts the same as a normal tensor constructor. Whilst the previously mentioned | ||||
| methods depend on the current GPU context, :meth:`~torch.Tensor.new` preserves | ||||
| the device of the original tensor. | ||||
| the same device, then you can use a ``torch.Tensor.new_*`` method | ||||
| (see :class:`torch.Tensor`). | ||||
| Whilst the previously mentioned ``torch.*`` factory functions | ||||
| (:ref:`tensor-creation-ops`) depend on the current GPU context and | ||||
| the attributes arguments you pass in, ``torch.Tensor.new_*`` methods preserve | ||||
| the device and other attributes of the tensor. | ||||
|  | ||||
| This is the recommended practice when creating modules in which new | ||||
| tensors/variables need to be created internally during the forward pass:: | ||||
| tensors need to be created internally during the forward pass. | ||||
|  | ||||
|     x_cpu = torch.FloatTensor(1) | ||||
|     x_gpu = torch.cuda.FloatTensor(1) | ||||
|     x_cpu_long = torch.LongTensor(1) | ||||
| :: | ||||
|  | ||||
|     cuda = torch.device('cuda') | ||||
|     x_cpu = torch.empty(2) | ||||
|     x_gpu = torch.empty(2, device=cuda) | ||||
|     x_cpu_long = torch.empty(2, dtype=torch.int64) | ||||
|  | ||||
|     y_cpu = x_cpu.new_full([3, 2], fill_value=0.3) | ||||
|     print(y_cpu) | ||||
|  | ||||
|         tensor([[ 0.3000,  0.3000], | ||||
|                 [ 0.3000,  0.3000], | ||||
|                 [ 0.3000,  0.3000]]) | ||||
|  | ||||
|     y_gpu = x_gpu.new_full([3, 2], fill_value=-5) | ||||
|     print(y_gpu) | ||||
|  | ||||
|         tensor([[-5.0000, -5.0000], | ||||
|                 [-5.0000, -5.0000], | ||||
|                 [-5.0000, -5.0000]], device='cuda:0') | ||||
|  | ||||
|     y_cpu_long = x_cpu_long.new_tensor([[1, 2, 3]]) | ||||
|     print(y_cpu_long) | ||||
|  | ||||
|         tensor([[ 1,  2,  3]]) | ||||
|  | ||||
|     y_cpu = x_cpu.new(8, 10, 10).fill_(0.3) | ||||
|     y_gpu = x_gpu.new(x_gpu.size()).fill_(-5) | ||||
|     y_cpu_long = x_cpu_long.new([[1, 2, 3]]) | ||||
|  | ||||
| If you want to create a tensor of the same type and size of another tensor, and | ||||
| fill it with either ones or zeros, :meth:`~torch.ones_like` or | ||||
| :meth:`~torch.zeros_like` are provided as convenient helper functions (which | ||||
| also preserve device):: | ||||
| also preserve :class:`torch.device` and :class:`torch.dtype` of a Tensor). | ||||
|  | ||||
|     x_cpu = torch.FloatTensor(1) | ||||
|     x_gpu = torch.cuda.FloatTensor(1) | ||||
| :: | ||||
|  | ||||
|     x_cpu = torch.empty(2, 3) | ||||
|     x_gpu = torch.empty(2, 3) | ||||
|  | ||||
|     y_cpu = torch.ones_like(x_cpu) | ||||
|     y_gpu = torch.zeros_like(x_gpu) | ||||
| @ -204,7 +248,7 @@ memory. CPU tensors and storages expose a :meth:`~torch.Tensor.pin_memory` | ||||
| method, that returns a copy of the object, with data put in a pinned region. | ||||
|  | ||||
| Also, once you pin a tensor or storage, you can use asynchronous GPU copies. | ||||
| Just pass an additional ``async=True`` argument to a :meth:`~torch.Tensor.cuda` | ||||
| Just pass an additional ``non_blocking=True`` argument to a :meth:`~torch.Tensor.cuda` | ||||
| call. This can be used to overlap data transfers with computation. | ||||
|  | ||||
| You can make the :class:`~torch.utils.data.DataLoader` return batches placed in | ||||
|  | ||||
| @ -9,8 +9,8 @@ memory and will only send a handle to another process. | ||||
|  | ||||
| .. note:: | ||||
|  | ||||
|     When a :class:`~torch.autograd.Variable` is sent to another process, both | ||||
|     the :attr:`Variable.data` and :attr:`Variable.grad.data` are going to be | ||||
|     When a :class:`~torch.Tensor` is sent to another process, both | ||||
|     the :attr:`~torch.Tensor` data and :attr:`torch.Tensor.grad` are going to be | ||||
|     shared. | ||||
|  | ||||
| This allows to implement various training methods, like Hogwild, A3C, or any | ||||
|  | ||||
							
								
								
									
										261
									
								
								docs/source/notes/windows.rst
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										261
									
								
								docs/source/notes/windows.rst
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,261 @@ | ||||
| Windows FAQ | ||||
| ========================== | ||||
|  | ||||
| Building from source | ||||
| -------------------- | ||||
|  | ||||
| Include optional components | ||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| There are two supported components for Windows PyTorch: | ||||
| MKL and MAGMA. Here are the steps to build with them. | ||||
|  | ||||
| .. code-block:: bat | ||||
|  | ||||
|     REM Make sure you have 7z and curl installed. | ||||
|  | ||||
|     REM Download MKL files | ||||
|     curl https://s3.amazonaws.com/ossci-windows/mkl_2018.2.185.7z -k -O | ||||
|     7z x -aoa mkl_2018.2.185.7z -omkl | ||||
|  | ||||
|     REM Download MAGMA files | ||||
|     REM cuda90/cuda91 is also available in the following line. | ||||
|     set CUDA_PREFIX=cuda80  | ||||
|     curl -k https://s3.amazonaws.com/ossci-windows/magma_%CUDA_PREFIX%_release_mkl_2018.2.185.7z -o magma.7z | ||||
|     7z x -aoa magma.7z -omagma | ||||
|      | ||||
|     REM Setting essential environment variables | ||||
|     set "CMAKE_INCLUDE_PATH=%cd%\\mkl\\include" | ||||
|     set "LIB=%cd%\\mkl\\lib;%LIB%" | ||||
|     set "MAGMA_HOME=%cd%\\magma" | ||||
|  | ||||
| Speeding CUDA build for Windows | ||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| Visual Studio doesn't support parallel custom task currently. | ||||
| As an alternative, we can use ``Ninja`` to parallelize CUDA | ||||
| build tasks. It can be used by typing only a few lines of code. | ||||
|  | ||||
| .. code-block:: bat | ||||
|      | ||||
|     REM Let's install ninja first. | ||||
|     pip install ninja | ||||
|  | ||||
|     REM Set it as the cmake generator | ||||
|     set CMAKE_GENERATOR=Ninja | ||||
|  | ||||
|  | ||||
| One key install script | ||||
| ^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| You can take a look at the script `here | ||||
| <https://github.com/peterjc123/pytorch-scripts>`_.  | ||||
| It will lead the way for you. | ||||
|  | ||||
| Extension | ||||
| --------- | ||||
|  | ||||
| CFFI Extension | ||||
| ^^^^^^^^^^^^^^ | ||||
|  | ||||
| The support for CFFI Extension is very experimental. There're  | ||||
| generally two steps to enable it under Windows. | ||||
|  | ||||
| First, specify additional ``libraries`` in ``Extension`` | ||||
| object to make it build on Windows. | ||||
|  | ||||
| .. code-block:: python | ||||
|  | ||||
|    ffi = create_extension( | ||||
|        '_ext.my_lib', | ||||
|        headers=headers, | ||||
|        sources=sources, | ||||
|        define_macros=defines, | ||||
|        relative_to=__file__, | ||||
|        with_cuda=with_cuda, | ||||
|        extra_compile_args=["-std=c99"], | ||||
|        libraries=['ATen', '_C'] # Append cuda libaries when necessary, like cudart | ||||
|    ) | ||||
|  | ||||
| Second, here is a workground for "unresolved external symbol  | ||||
| state caused by ``extern THCState *state;``" | ||||
|  | ||||
| Change the source code from C to C++. An example is listed below. | ||||
|  | ||||
| .. code-block:: cpp | ||||
|  | ||||
|     #include <THC/THC.h> | ||||
|     #include <ATen/ATen.h> | ||||
|  | ||||
|     THCState *state = at::globalContext().thc_state; | ||||
|  | ||||
|     extern "C" int my_lib_add_forward_cuda(THCudaTensor *input1, THCudaTensor *input2, | ||||
|                                             THCudaTensor *output) | ||||
|     { | ||||
|         if (!THCudaTensor_isSameSizeAs(state, input1, input2)) | ||||
|         return 0; | ||||
|         THCudaTensor_resizeAs(state, output, input1); | ||||
|         THCudaTensor_cadd(state, output, input1, 1.0, input2); | ||||
|         return 1; | ||||
|     } | ||||
|  | ||||
|     extern "C" int my_lib_add_backward_cuda(THCudaTensor *grad_output, THCudaTensor *grad_input) | ||||
|     { | ||||
|         THCudaTensor_resizeAs(state, grad_input, grad_output); | ||||
|         THCudaTensor_fill(state, grad_input, 1); | ||||
|         return 1; | ||||
|     } | ||||
|  | ||||
| Cpp Extension | ||||
| ^^^^^^^^^^^^^ | ||||
|  | ||||
| This type of extension has better support compared with | ||||
| the previous one. However, it still needs some manual | ||||
| configuration. First, you should open the | ||||
| **x86_x64 Cross Tools Command Prompt for VS 2017**. | ||||
| And then, you can open the Git-Bash in it. It is | ||||
| usually located in ``C:\Program Files\Git\git-bash.exe``. | ||||
| Finally, you can start your compiling process. | ||||
|  | ||||
| Installation | ||||
| ------------ | ||||
|  | ||||
| Package not found in win-32 channel. | ||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| .. code-block:: bat | ||||
|  | ||||
|     Solving environment: failed | ||||
|  | ||||
|     PackagesNotFoundError: The following packages are not available from current channels: | ||||
|  | ||||
|     - pytorch | ||||
|  | ||||
|     Current channels: | ||||
|     - https://conda.anaconda.org/pytorch/win-32 | ||||
|     - https://conda.anaconda.org/pytorch/noarch | ||||
|     - https://repo.continuum.io/pkgs/main/win-32 | ||||
|     - https://repo.continuum.io/pkgs/main/noarch | ||||
|     - https://repo.continuum.io/pkgs/free/win-32 | ||||
|     - https://repo.continuum.io/pkgs/free/noarch | ||||
|     - https://repo.continuum.io/pkgs/r/win-32 | ||||
|     - https://repo.continuum.io/pkgs/r/noarch | ||||
|     - https://repo.continuum.io/pkgs/pro/win-32 | ||||
|     - https://repo.continuum.io/pkgs/pro/noarch | ||||
|     - https://repo.continuum.io/pkgs/msys2/win-32 | ||||
|     - https://repo.continuum.io/pkgs/msys2/noarch | ||||
|  | ||||
| PyTorch doesn't work on 32-bit system. Please use Windows and | ||||
| Python 64-bit version. | ||||
|  | ||||
| Why are there no Python 2 packages for Windows? | ||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| Because it's not stable enough. There're some issues that need to | ||||
| be solved before we officially release it. You can build it by yourself. | ||||
|  | ||||
| Import error | ||||
| ^^^^^^^^^^^^ | ||||
|  | ||||
| .. code-block:: py3tb | ||||
|  | ||||
|     from torch._C import * | ||||
|  | ||||
|     ImportError: DLL load failed: The specified module could not be found. | ||||
|  | ||||
|  | ||||
| The problem is caused by the missing of the essential files. Actually, | ||||
| we include almost all the essential files that PyTorch need except VC2017 | ||||
| redistributable. You can resolve this by typing the following command. | ||||
|  | ||||
| .. code-block:: bat | ||||
|  | ||||
|     conda install -c peterjc123 vc vs2017_runtime | ||||
|  | ||||
| Another possible cause may be you are using GPU version without NVIDIA | ||||
| graphics cards. Please replace your GPU package with the CPU one. | ||||
|  | ||||
| Usage (multiprocessing) | ||||
| ------------------------------------------------------- | ||||
|  | ||||
| Multiprocessing error without if-clause protection | ||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| .. code-block:: py3tb | ||||
|  | ||||
|     RuntimeError: | ||||
|    	An attempt has been made to start a new process before the | ||||
|    	current process has finished its bootstrapping phase. | ||||
|  | ||||
|        This probably means that you are not using fork to start your | ||||
|        child processes and you have forgotten to use the proper idiom | ||||
|        in the main module: | ||||
|  | ||||
|            if __name__ == '__main__': | ||||
|                freeze_support() | ||||
|                ... | ||||
|  | ||||
|        The "freeze_support()" line can be omitted if the program | ||||
|        is not going to be frozen to produce an executable. | ||||
|  | ||||
| The implementation of ``multiprocessing`` is different on Windows, which | ||||
| uses ``spawn`` instead of ``fork``. So we have to wrap the code with an | ||||
| if-clause to protect the code from executing multiple times. Refactor | ||||
| your code into the following structure. | ||||
|  | ||||
| .. code-block:: python | ||||
|  | ||||
|     import torch | ||||
|  | ||||
|     def main() | ||||
|         for i, data in enumerate(dataloader): | ||||
|             # do something here | ||||
|  | ||||
|     if __name__ == '__main__': | ||||
|         main() | ||||
|  | ||||
|  | ||||
| Multiprocessing error "Broken pipe" | ||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| .. code-block:: py3tb | ||||
|  | ||||
|     ForkingPickler(file, protocol).dump(obj) | ||||
|  | ||||
|     BrokenPipeError: [Errno 32] Broken pipe | ||||
|  | ||||
| This issue happens when the child process ends before the parent process | ||||
| finishes sending data. There may be something wrong with your code. You | ||||
| can debug your code by reducing the ``num_worker`` of  | ||||
| :class:`~torch.utils.data.DataLoader` to zero and see if the issue persists. | ||||
|  | ||||
| Multiprocessing error "driver shut down" | ||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| .. code-block:: py3tb | ||||
|  | ||||
|     Couldn’t open shared file mapping: <torch_14808_1591070686>, error code: <1455> at torch\lib\TH\THAllocator.c:154 | ||||
|  | ||||
|     [windows] driver shut down | ||||
|  | ||||
| Please update your graphics driver. If this persists, this may be that your | ||||
| graphics card is too old or the calculation is too heavy for your card. Please | ||||
| update the TDR settings according to this `post | ||||
| <https://www.pugetsystems.com/labs/hpc/Working-around-TDR-in-Windows-for-a-better-GPU-computing-experience-777/>`_. | ||||
|  | ||||
| CUDA IPC operations | ||||
| ^^^^^^^^^^^^^^^^^^^ | ||||
|  | ||||
| .. code-block:: py3tb | ||||
|  | ||||
|    THCudaCheck FAIL file=torch\csrc\generic\StorageSharing.cpp line=252 error=63 : OS call failed or operation not supported on this OS | ||||
|  | ||||
| They are not supported on Windows. Something like doing multiprocessing on CUDA | ||||
| tensors cannot succeed, there are two alternatives for this. | ||||
|  | ||||
| 1. Don't use ``multiprocessing``. Set the ``num_worker`` of  | ||||
| :class:`~torch.utils.data.DataLoader` to zero. | ||||
|  | ||||
| 2. Share CPU tensors instead. Make sure your custom | ||||
| :class:`~torch.utils.data.DataSet` returns CPU tensors. | ||||
|  | ||||
| @ -1,5 +1,7 @@ | ||||
| .. currentmodule:: torch.sparse | ||||
|  | ||||
| .. _sparse-docs: | ||||
|  | ||||
| torch.sparse | ||||
| ============ | ||||
|  | ||||
|  | ||||
							
								
								
									
										131
									
								
								docs/source/tensor_attributes.rst
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										131
									
								
								docs/source/tensor_attributes.rst
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,131 @@ | ||||
| .. currentmodule:: torch | ||||
|  | ||||
| .. _tensor-attributes-doc: | ||||
|  | ||||
| Tensor Attributes | ||||
| ================= | ||||
|  | ||||
| Each ``torch.Tensor`` has a :class:`torch.dtype`, :class:`torch.device`, and :class:`torch.layout`. | ||||
|  | ||||
| .. _dtype-doc: | ||||
|  | ||||
| torch.dtype | ||||
| ----------- | ||||
|  | ||||
| .. class:: torch.dtype | ||||
|  | ||||
| A :class:`torch.dtype` is an object that represents the data type of a | ||||
| :class:`torch.Tensor`. PyTorch has eight different data types: | ||||
|  | ||||
| ========================   ===========================================   =========================== | ||||
| Data type                  dtype                                         Tensor types | ||||
| ========================   ===========================================   =========================== | ||||
| 32-bit floating point      ``torch.float32`` or ``torch.float``          ``torch.*.FloatTensor`` | ||||
| 64-bit floating point      ``torch.float64`` or ``torch.double``         ``torch.*.DoubleTensor`` | ||||
| 16-bit floating point      ``torch.float16`` or ``torch.half``           ``torch.*.HalfTensor`` | ||||
| 8-bit integer (unsigned)   ``torch.uint8``                               ``torch.*.ByteTensor`` | ||||
| 8-bit integer (signed)     ``torch.int8``                                ``torch.*.CharTensor`` | ||||
| 16-bit integer (signed)    ``torch.int16`` or ``torch.short``            ``torch.*.ShortTensor`` | ||||
| 32-bit integer (signed)    ``torch.int32`` or ``torch.int``              ``torch.*.IntTensor`` | ||||
| 64-bit integer (signed)    ``torch.int64`` or ``torch.long``             ``torch.*.LongTensor`` | ||||
| ========================   ===========================================   =========================== | ||||
|  | ||||
| .. _device-doc: | ||||
|  | ||||
| torch.device | ||||
| ------------ | ||||
|  | ||||
| .. class:: torch.device | ||||
|  | ||||
| A :class:`torch.device` is an object representing the device on which a :class:`torch.Tensor` is | ||||
| or will be allocated. | ||||
|  | ||||
| The :class:`torch.device` contains a device type (``'cpu'`` or ``'cuda'``) and optional device ordinal for the | ||||
| device type.  If the device ordinal is not present, this represents the current device for the device type; | ||||
| e.g. a :class:`torch.Tensor` constructed with device ``'cuda'`` is equivalent to ``'cuda:X'`` where X is the result of | ||||
| :func:`torch.cuda.current_device()`. | ||||
|  | ||||
| A :class:`torch.Tensor`'s device can be accessed via the :attr:`Tensor.device` property. | ||||
|  | ||||
| A :class:`torch.device` can be constructed via a string or via a string and device ordinal | ||||
|  | ||||
| Via a string: | ||||
| :: | ||||
|  | ||||
|     >>> torch.device('cuda:0') | ||||
|     device(type='cuda', index=0) | ||||
|  | ||||
|     >>> torch.device('cpu') | ||||
|     device(type='cpu') | ||||
|  | ||||
|     >>> torch.device('cuda')  # current cuda device | ||||
|     device(type='cuda') | ||||
|  | ||||
| Via a string and device ordinal: | ||||
|  | ||||
| :: | ||||
|  | ||||
|     >>> torch.device('cuda', 0) | ||||
|     device(type='cuda', index=0) | ||||
|  | ||||
|     >>> torch.device('cpu', 0) | ||||
|     device(type='cpu', index=0) | ||||
|  | ||||
| .. note:: | ||||
|    The :class:`torch.device` argument in functions can generally be substituted with a string. | ||||
|    This allows for fast prototyping of code. | ||||
|  | ||||
|    >>> # Example of a function that takes in a torch.device | ||||
|    >>> cuda1 = torch.device('cuda:1') | ||||
|    >>> torch.randn((2,3), device=cuda1) | ||||
|  | ||||
|    >>> # You can substitute the torch.device with a string | ||||
|    >>> torch.randn((2,3), 'cuda:1') | ||||
|  | ||||
| .. note:: | ||||
|    For legacy reasons, a device can be constructed via a single device ordinal, which is treated | ||||
|    as a cuda device.  This matches :meth:`Tensor.get_device`, which returns an ordinal for cuda | ||||
|    tensors and is not supported for cpu tensors. | ||||
|  | ||||
|    >>> torch.device(1) | ||||
|    device(type='cuda', index=1) | ||||
|  | ||||
| .. note:: | ||||
|    Methods which take a device will generally accept a (properly formatted) string | ||||
|    or (legacy) integer device ordinal, i.e. the following are all equivalent: | ||||
|  | ||||
|    >>> torch.randn((2,3), device=torch.device('cuda:1')) | ||||
|    >>> torch.randn((2,3), device='cuda:1') | ||||
|    >>> torch.randn((2,3), device=1)  # legacy | ||||
|  | ||||
|  | ||||
| .. _layout-doc: | ||||
|  | ||||
| torch.layout | ||||
| ------------ | ||||
|  | ||||
| .. class:: torch.layout | ||||
|  | ||||
| A :class:`torch.layout` is an object that represents the memory layout of a | ||||
| :class:`torch.Tensor`. Currently, we support ``torch.strided`` (dense Tensors) | ||||
| and have experimental support for ``torch.sparse_coo`` (sparse COO Tensors). | ||||
|  | ||||
| ``torch.strided`` represents dense Tensors and is the memory layout that | ||||
| is most commonly used. Each strided tensor has an associated | ||||
| :class:`torch.Storage`, which holds its data. These tensors provide | ||||
| multi-dimensional, `strided <https://en.wikipedia.org/wiki/Stride_of_an_array>`_ | ||||
| view of a storage. Strides are a list of integers: the k-th stride | ||||
| represents the jump in the memory necessary to go from one element to the | ||||
| next one in the k-th dimension of the Tensor. This concept makes it possible | ||||
| to perform many tensor operations efficiently. | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor([[1, 2, 3, 4, 5], [6, 7, 8, 9, 10]]) | ||||
|     >>> x.stride() | ||||
|     (5, 1) | ||||
|  | ||||
|     >>> x.t().stride() | ||||
|     (1, 5) | ||||
|  | ||||
| For more information on ``torch.sparse_coo`` tensors, see :ref:`sparse-docs`. | ||||
| @ -10,18 +10,18 @@ a single data type. | ||||
|  | ||||
| Torch defines eight CPU tensor types and eight GPU tensor types: | ||||
|  | ||||
| ========================   ===================   ===========================   ================================ | ||||
| Data type                  dtype                         CPU tensor                    GPU tensor | ||||
| ========================   ===================   ===========================   ================================ | ||||
| 32-bit floating point      ``torch.float32``     :class:`torch.FloatTensor`    :class:`torch.cuda.FloatTensor` | ||||
| 64-bit floating point      ``torch.float64``     :class:`torch.DoubleTensor`   :class:`torch.cuda.DoubleTensor` | ||||
| 16-bit floating point      ``torch.float16``     :class:`torch.HalfTensor`     :class:`torch.cuda.HalfTensor` | ||||
| 8-bit integer (unsigned)   ``torch.uint8``       :class:`torch.ByteTensor`     :class:`torch.cuda.ByteTensor` | ||||
| 8-bit integer (signed)     ``torch.int8``        :class:`torch.CharTensor`     :class:`torch.cuda.CharTensor` | ||||
| 16-bit integer (signed)    ``torch.int16``       :class:`torch.ShortTensor`    :class:`torch.cuda.ShortTensor` | ||||
| 32-bit integer (signed)    ``torch.int32``       :class:`torch.IntTensor`      :class:`torch.cuda.IntTensor` | ||||
| 64-bit integer (signed)    ``torch.int64``       :class:`torch.LongTensor`     :class:`torch.cuda.LongTensor` | ||||
| ========================   ===================   ===========================   ================================ | ||||
| ========================   ===========================================   ===========================   ================================ | ||||
| Data type                  dtype                                         CPU tensor                    GPU tensor | ||||
| ========================   ===========================================   ===========================   ================================ | ||||
| 32-bit floating point      ``torch.float32`` or ``torch.float``          :class:`torch.FloatTensor`    :class:`torch.cuda.FloatTensor` | ||||
| 64-bit floating point      ``torch.float64`` or ``torch.double``         :class:`torch.DoubleTensor`   :class:`torch.cuda.DoubleTensor` | ||||
| 16-bit floating point      ``torch.float16`` or ``torch.half``           :class:`torch.HalfTensor`     :class:`torch.cuda.HalfTensor` | ||||
| 8-bit integer (unsigned)   ``torch.uint8``                               :class:`torch.ByteTensor`     :class:`torch.cuda.ByteTensor` | ||||
| 8-bit integer (signed)     ``torch.int8``                                :class:`torch.CharTensor`     :class:`torch.cuda.CharTensor` | ||||
| 16-bit integer (signed)    ``torch.int16`` or ``torch.short``            :class:`torch.ShortTensor`    :class:`torch.cuda.ShortTensor` | ||||
| 32-bit integer (signed)    ``torch.int32`` or ``torch.int``              :class:`torch.IntTensor`      :class:`torch.cuda.IntTensor` | ||||
| 64-bit integer (signed)    ``torch.int64`` or ``torch.long``             :class:`torch.LongTensor`     :class:`torch.cuda.LongTensor` | ||||
| ========================   ===========================================   ===========================   ================================ | ||||
|  | ||||
| :class:`torch.Tensor` is an alias for the default tensor type (:class:`torch.FloatTensor`). | ||||
|  | ||||
| @ -31,16 +31,20 @@ A tensor can be constructed from a Python :class:`list` or sequence using the | ||||
| :: | ||||
|  | ||||
|     >>> torch.tensor([[1., -1.], [1., -1.]]) | ||||
|  | ||||
|      1 -1 | ||||
|      1 -1 | ||||
|     [torch.FloatTensor of size (2,2)] | ||||
|  | ||||
|     tensor([[ 1.0000, -1.0000], | ||||
|             [ 1.0000, -1.0000]]) | ||||
|     >>> torch.tensor(np.array([[1, 2, 3], [4, 5, 6]])) | ||||
|     tensor([[ 1,  2,  3], | ||||
|             [ 4,  5,  6]]) | ||||
|  | ||||
|      1 -1 | ||||
|      1 -1 | ||||
|     [torch.FloatTensor of size (2,2)] | ||||
| .. warning:: | ||||
|  | ||||
|     :func:`torch.tensor` always copies :attr:`data`. If you have a Tensor | ||||
|     :attr:`data` and just want to change its ``requires_grad`` flag, use | ||||
|     :meth:`~torch.Tensor.requires_grad_` or | ||||
|     :meth:`~torch.Tensor.detach` to avoid a copy. | ||||
|     If you have a numpy array and want to avoid a copy, use | ||||
|     :func:`torch.from_numpy`. | ||||
|  | ||||
| An tensor of specific data type can be constructed by passing a | ||||
| :class:`torch.dtype` and/or a :class:`torch.device` to a | ||||
| @ -49,16 +53,12 @@ constructor or tensor creation op: | ||||
| :: | ||||
|  | ||||
|     >>> torch.zeros([2, 4], dtype=torch.int32) | ||||
|  | ||||
|     0  0  0  0 | ||||
|     0  0  0  0 | ||||
|     [torch.IntTensor of size 2x4] | ||||
|  | ||||
|     >>> torch.ones([2, 4], dtype=torch.float64, device=torch.device('cuda:0')) | ||||
|  | ||||
|     1  1  1  1 | ||||
|     1  1  1  1 | ||||
|     [torch.cuda.DoubleTensor of size 2x4] | ||||
|     tensor([[ 0,  0,  0,  0], | ||||
|             [ 0,  0,  0,  0]], dtype=torch.int32) | ||||
|     >>> cuda0 = torch.device('cuda:0') | ||||
|     >>> torch.ones([2, 4], dtype=torch.float64, device=cuda0) | ||||
|     tensor([[ 1.0000,  1.0000,  1.0000,  1.0000], | ||||
|             [ 1.0000,  1.0000,  1.0000,  1.0000]], dtype=torch.float64, device='cuda:0') | ||||
|  | ||||
| The contents of a tensor can be accessed and modified using Python's indexing | ||||
| and slicing notation: | ||||
| @ -67,14 +67,27 @@ and slicing notation: | ||||
|  | ||||
|     >>> x = torch.tensor([[1, 2, 3], [4, 5, 6]]) | ||||
|     >>> print(x[1][2]) | ||||
|  | ||||
|     6.0 | ||||
|     tensor(6) | ||||
|     >>> x[0][1] = 8 | ||||
|     >>> print(x) | ||||
|     tensor([[ 1,  8,  3], | ||||
|             [ 4,  5,  6]]) | ||||
|  | ||||
|      1  8  3 | ||||
|      4  5  6 | ||||
|     [torch.FloatTensor of size 2x3] | ||||
| Use :meth:`torch.Tensor.item` to get a Python number from a tensor containing a | ||||
| single value: | ||||
|  | ||||
| :: | ||||
|  | ||||
|     >>> x = torch.tensor([[1]]) | ||||
|     >>> x | ||||
|     tensor([[ 1]]) | ||||
|     >>> x.item() | ||||
|     1 | ||||
|     >>> x = torch.tensor(2.5) | ||||
|     >>> x | ||||
|     tensor(2.5000) | ||||
|     >>> x.item() | ||||
|     2.5 | ||||
|  | ||||
| A tensor can be created with :attr:`requires_grad=True` so that | ||||
| :mod:`torch.autograd` records operations on them for automatic differentiation. | ||||
| @ -84,26 +97,47 @@ A tensor can be created with :attr:`requires_grad=True` so that | ||||
|     >>> x = torch.tensor([[1., -1.], [1., 1.]], requires_grad=True) | ||||
|     >>> out = x.pow(2).sum() | ||||
|     >>> out.backward() | ||||
|     >>> out.grad | ||||
|  | ||||
|      2 -2 | ||||
|      2  2 | ||||
|     [torch.FloatTensor of size (2,2)] | ||||
|     >>> x.grad | ||||
|     tensor([[ 2.0000, -2.0000], | ||||
|             [ 2.0000,  2.0000]]) | ||||
|  | ||||
| Each tensor has an associated :class:`torch.Storage`, which holds its data. | ||||
| The tensor class provides multi-dimensional, `strided <https://en.wikipedia.org/wiki/Stride_of_an_array>`_ | ||||
| view of a storage and defines numeric operations on it. | ||||
|  | ||||
| .. note:: | ||||
|    For more information on the :class:`torch.dtype`, :class:`torch.device`, and | ||||
|    :class:`torch.layout` attributes of a :class:`torch.Tensor`, see | ||||
|    :ref:`tensor-attributes-doc`. | ||||
|  | ||||
| .. note:: | ||||
|    Methods which mutate a tensor are marked with an underscore suffix. | ||||
|    For example, :func:`torch.FloatTensor.abs_` computes the absolute value | ||||
|    in-place and returns the modified tensor, while :func:`torch.FloatTensor.abs` | ||||
|    computes the result in a new tensor. | ||||
|  | ||||
| .. note:: | ||||
|     To change an existing tensor's :class:`torch.device` and/or :class:`torch.dtype`, consider using | ||||
|     :meth:`~torch.Tensor.to` method on the tensor. | ||||
|  | ||||
| .. class:: Tensor() | ||||
|  | ||||
|   Create a tensor using the :func:`torch.tensor` constructor or with | ||||
|   tensor creation ops (see :ref:`tensor-creation-ops`) | ||||
|    There are a few main ways to create a tensor, depending on your use case. | ||||
|  | ||||
|    - To create a tensor with pre-existing data, use :func:`torch.tensor`. | ||||
|    - To create a tensor with specific size, use ``torch.*`` tensor creation | ||||
|      ops (see :ref:`tensor-creation-ops`). | ||||
|    - To create a tensor with the same size (and similar types) as another tensor, | ||||
|      use ``torch.*_like`` tensor creation ops | ||||
|      (see :ref:`tensor-creation-ops`). | ||||
|    - To create a tensor with similar type but different size as another tensor, | ||||
|      use ``tensor.new_*`` creation ops. | ||||
|  | ||||
|    .. automethod:: new_tensor | ||||
|    .. automethod:: new_full | ||||
|    .. automethod:: new_empty | ||||
|    .. automethod:: new_ones | ||||
|    .. automethod:: new_zeros | ||||
|  | ||||
|    .. automethod:: abs | ||||
|    .. automethod:: abs_ | ||||
| @ -262,7 +296,6 @@ view of a storage and defines numeric operations on it. | ||||
|    .. automethod:: neg | ||||
|    .. automethod:: neg_ | ||||
|    .. automethod:: nelement | ||||
|    .. automethod:: new | ||||
|    .. automethod:: nonzero | ||||
|    .. automethod:: norm | ||||
|    .. automethod:: normal_ | ||||
| @ -289,6 +322,7 @@ view of a storage and defines numeric operations on it. | ||||
|    .. automethod:: renorm | ||||
|    .. automethod:: renorm_ | ||||
|    .. automethod:: repeat | ||||
|    .. automethod:: requires_grad_ | ||||
|    .. automethod:: reshape | ||||
|    .. automethod:: resize_ | ||||
|    .. automethod:: resize_as_ | ||||
| @ -329,6 +363,7 @@ view of a storage and defines numeric operations on it. | ||||
|    .. automethod:: symeig | ||||
|    .. automethod:: t | ||||
|    .. automethod:: t_ | ||||
|    .. automethod:: to | ||||
|    .. automethod:: take | ||||
|    .. automethod:: tan | ||||
|    .. automethod:: tan_ | ||||
|  | ||||
| @ -6,8 +6,9 @@ Tensors | ||||
| ---------------------------------- | ||||
| .. autofunction:: is_tensor | ||||
| .. autofunction:: is_storage | ||||
| .. autofunction:: set_default_tensor_type | ||||
| .. autofunction:: set_default_dtype | ||||
| .. autofunction:: get_default_dtype | ||||
| .. autofunction:: set_default_tensor_type | ||||
| .. autofunction:: numel | ||||
| .. autofunction:: set_printoptions | ||||
| .. autofunction:: set_flush_denormal | ||||
| @ -27,6 +28,9 @@ Creation Ops | ||||
|     :func:`torch.randint` | ||||
|     :func:`torch.randint_like` | ||||
|     :func:`torch.randperm` | ||||
|     You may also use :func:`torch.empty` with the :ref:`inplace-random-sampling` | ||||
|     methods to create :class:`torch.Tensor` s with values sampled from a broader | ||||
|     range of distributions. | ||||
|  | ||||
| .. autofunction:: tensor | ||||
| .. autofunction:: from_numpy | ||||
| @ -83,6 +87,8 @@ Random sampling | ||||
| .. autofunction:: randn_like | ||||
| .. autofunction:: randperm | ||||
|  | ||||
| .. _inplace-random-sampling: | ||||
|  | ||||
| In-place random sampling | ||||
| ~~~~~~~~~~~~~~~~~~~~~~~~ | ||||
|  | ||||
| @ -109,6 +115,37 @@ Parallelism | ||||
| .. autofunction:: get_num_threads | ||||
| .. autofunction:: set_num_threads | ||||
|  | ||||
| Locally disabling gradient computation | ||||
| -------------------------------------- | ||||
| The context managers :func:`torch.no_grad`, :func:`torch.enable_grad`, and | ||||
| :func:`torch.set_grad_enabled` are helpful for locally disabling and enabling | ||||
| gradient computation. See :ref:`locally-disable-grad` for more details on | ||||
| their usage. | ||||
|  | ||||
| Examples:: | ||||
|  | ||||
|   >>> x = torch.zeros(1, requires_grad=True) | ||||
|   >>> with torch.no_grad(): | ||||
|   ...     y = x * 2 | ||||
|   >>> y.requires_grad | ||||
|   False | ||||
|  | ||||
|   >>> is_train = False | ||||
|   >>> with torch.set_grad_enabled(is_train): | ||||
|   ...     y = x * 2 | ||||
|   >>> y.requires_grad | ||||
|   False | ||||
|  | ||||
|   >>> torch.set_grad_enabled(True)  # this can also be used as a function | ||||
|   >>> y = x * 2 | ||||
|   >>> y.requires_grad | ||||
|   True | ||||
|  | ||||
|   >>> torch.set_grad_enabled(False) | ||||
|   >>> y = x * 2 | ||||
|   >>> y.requires_grad | ||||
|   False | ||||
|  | ||||
|  | ||||
| Math operations | ||||
| ---------------------------------- | ||||
|  | ||||
							
								
								
									
										19
									
								
								setup.py
									
									
									
									
									
								
							
							
						
						
									
										19
									
								
								setup.py
									
									
									
									
									
								
							| @ -43,10 +43,6 @@ | ||||
| #   WITH_GLOO_IBVERBS | ||||
| #     toggle features related to distributed support | ||||
| # | ||||
| #   PYTORCH_BINARY_BUILD | ||||
| #     toggle static linking against libstdc++, used when we're building | ||||
| #     binaries for distribution | ||||
| # | ||||
| #   PYTORCH_BUILD_VERSION | ||||
| #   PYTORCH_BUILD_NUMBER | ||||
| #     specify the version of PyTorch, rather than the hard-coded version | ||||
| @ -780,19 +776,6 @@ if DEBUG: | ||||
|         extra_compile_args += ['-O0', '-g'] | ||||
|         extra_link_args += ['-O0', '-g'] | ||||
|  | ||||
| if os.getenv('PYTORCH_BINARY_BUILD') and platform.system() == 'Linux': | ||||
|     print('PYTORCH_BINARY_BUILD found. Static linking libstdc++ on Linux') | ||||
|     # get path of libstdc++ and link manually. | ||||
|     # for reasons unknown, -static-libstdc++ doesn't fully link some symbols | ||||
|     CXXNAME = os.getenv('CXX', 'g++') | ||||
|     STDCPP_LIB = subprocess.check_output([CXXNAME, '-print-file-name=libstdc++.a']) | ||||
|     STDCPP_LIB = STDCPP_LIB[:-1] | ||||
|     if type(STDCPP_LIB) != str:  # python 3 | ||||
|         STDCPP_LIB = STDCPP_LIB.decode(sys.stdout.encoding) | ||||
|     main_link_args += [STDCPP_LIB] | ||||
|     version_script = os.path.abspath("tools/pytorch.version") | ||||
|     extra_link_args += ['-Wl,--version-script=' + version_script] | ||||
|  | ||||
|  | ||||
| def make_relative_rpath(path): | ||||
|     if IS_DARWIN: | ||||
| @ -807,7 +790,7 @@ def make_relative_rpath(path): | ||||
| ################################################################################ | ||||
|  | ||||
| extensions = [] | ||||
| packages = find_packages(exclude=('tools', 'tools.*', 'caffe2', 'caffe')) | ||||
| packages = find_packages(exclude=('tools', 'tools.*', 'caffe2', 'caffe2.*', 'caffe', 'caffe.*')) | ||||
| C = Extension("torch._C", | ||||
|               libraries=main_libraries, | ||||
|               sources=main_sources, | ||||
|  | ||||
| @ -8,7 +8,7 @@ import warnings | ||||
| from copy import deepcopy | ||||
| from collections import OrderedDict | ||||
| from itertools import product | ||||
| from operator import mul | ||||
| from operator import mul, itemgetter | ||||
| from functools import reduce, wraps | ||||
| from torch.autograd.gradcheck import gradgradcheck, gradcheck | ||||
| from torch.autograd.function import once_differentiable | ||||
| @ -1289,6 +1289,12 @@ class TestAutograd(TestCase): | ||||
|         Identity.apply(v).backward() | ||||
|         self.assertEqual(device[0], 1) | ||||
|  | ||||
|     @unittest.skipIf(torch.cuda.device_count() < 2, "no multi-GPU") | ||||
|     def test_inputbuffer_add_multigpu(self): | ||||
|         input = torch.randn(1).cuda(0).requires_grad_() | ||||
|         output = input.cuda(1) + input.cuda(1) | ||||
|         output.backward() | ||||
|  | ||||
|     def test_detach(self): | ||||
|         x = torch.randn(10, 10, requires_grad=True) | ||||
|         y = x + 2 | ||||
| @ -2267,9 +2273,9 @@ S = 5 | ||||
| #   method name, | ||||
| #   input size/constructing fn, | ||||
| #   args (tuple represents shape of a tensor arg), | ||||
| #   test variant name (will be used at test name suffix),  // optional | ||||
| #   indices for possible dim arg,                          // optional | ||||
| #   output indices that should be gradcheck'ed,            // optional | ||||
| #   test variant name (will be used at test name suffix),    // optional | ||||
| #   indices for possible dim arg,                            // optional | ||||
| #   fn mapping output to part that should be gradcheck'ed,   // optional | ||||
| # ) | ||||
| method_tests = [ | ||||
|     ('add', (S, S, S), ((S, S, S),)), | ||||
| @ -2700,18 +2706,31 @@ method_tests = [ | ||||
|      'symmetric_pd', NO_ARGS, [skipIfNoLapack]), | ||||
|     ('logdet', lambda: make_nonzero_det(random_fullrank_matrix_distinct_singular_value(S), 1, 0), NO_ARGS, | ||||
|      'distinct_singular_values', NO_ARGS, [skipIfNoLapack]), | ||||
|     ('slogdet', lambda: make_nonzero_det(torch.randn(1, 1), 1), NO_ARGS, '1x1_pos_det', NO_ARGS, [skipIfNoLapack], [1]), | ||||
|     ('slogdet', lambda: make_nonzero_det(torch.randn(1, 1), 1), NO_ARGS, | ||||
|      '1x1_pos_det', NO_ARGS, [skipIfNoLapack], itemgetter(1)), | ||||
|     ('slogdet', lambda: make_nonzero_det(torch.randn(1, 1), -1), NO_ARGS, | ||||
|      '1x1_neg_det', NO_ARGS, [skipIfNoLapack], [1]), | ||||
|     ('slogdet', lambda: make_nonzero_det(torch.randn(S, S), 1), NO_ARGS, 'pos_det', NO_ARGS, [skipIfNoLapack], [1]), | ||||
|     ('slogdet', lambda: make_nonzero_det(torch.randn(S, S), -1), NO_ARGS, 'neg_det', NO_ARGS, [skipIfNoLapack], [1]), | ||||
|      '1x1_neg_det', NO_ARGS, [skipIfNoLapack], itemgetter(1)), | ||||
|     ('slogdet', lambda: make_nonzero_det(torch.randn(S, S), 1), NO_ARGS, | ||||
|      'pos_det', NO_ARGS, [skipIfNoLapack], itemgetter(1)), | ||||
|     ('slogdet', lambda: make_nonzero_det(torch.randn(S, S), -1), NO_ARGS, | ||||
|      'neg_det', NO_ARGS, [skipIfNoLapack], itemgetter(1)), | ||||
|     ('slogdet', lambda: make_nonzero_det(random_symmetric_matrix(S)), NO_ARGS, | ||||
|      'symmetric', NO_ARGS, [skipIfNoLapack], [1]), | ||||
|     ('slogdet', lambda: random_symmetric_pd_matrix(S), NO_ARGS, 'symmetric_pd', NO_ARGS, [skipIfNoLapack], [1]), | ||||
|      'symmetric', NO_ARGS, [skipIfNoLapack], itemgetter(1)), | ||||
|     ('slogdet', lambda: random_symmetric_pd_matrix(S), NO_ARGS, | ||||
|      'symmetric_pd', NO_ARGS, [skipIfNoLapack], itemgetter(1)), | ||||
|     ('slogdet', lambda: random_fullrank_matrix_distinct_singular_value(S), NO_ARGS, | ||||
|      'distinct_singular_values', NO_ARGS, [skipIfNoLapack], [1]), | ||||
|      'distinct_singular_values', NO_ARGS, [skipIfNoLapack], itemgetter(1)), | ||||
|     ('svd', lambda: random_fullrank_matrix_distinct_singular_value(S), NO_ARGS, '', NO_ARGS, [skipIfNoLapack]), | ||||
|     ('svd', lambda: random_fullrank_matrix_distinct_singular_value(M), NO_ARGS, 'large', NO_ARGS, [skipIfNoLapack]), | ||||
|     ('svd', lambda: random_fullrank_matrix_distinct_singular_value(S)[:(S - 2)], NO_ARGS, | ||||
|      'wide', NO_ARGS, [skipIfNoLapack]), | ||||
|     ('svd', lambda: random_fullrank_matrix_distinct_singular_value(S)[:, :(S - 2)], NO_ARGS, | ||||
|      'tall', NO_ARGS, [skipIfNoLapack]), | ||||
|     ('svd', lambda: random_fullrank_matrix_distinct_singular_value(S)[:(S - 2)], (False,), | ||||
|      'wide_all', NO_ARGS, [skipIfNoLapack], lambda usv: (usv[0], usv[1], usv[2][:, :(S - 2)])), | ||||
|     ('svd', lambda: random_fullrank_matrix_distinct_singular_value(S)[:, :(S - 2)], (False,), | ||||
|      'tall_all', NO_ARGS, [skipIfNoLapack], lambda usv: (usv[0][:, :(S - 2)], usv[1], usv[2])), | ||||
|     ('svd', lambda: random_fullrank_matrix_distinct_singular_value(M), NO_ARGS, | ||||
|      'large', NO_ARGS, [skipIfNoLapack]), | ||||
|     ('gesv', (S, S), ((S, S),), '', NO_ARGS, [skipIfNoLapack]), | ||||
|     ('fill_', (S, S, S), (1,), 'number'), | ||||
|     ('fill_', (), (1,), 'number_scalar'), | ||||
| @ -3028,7 +3047,7 @@ for test in method_tests: | ||||
|  | ||||
|     skipTestIf = test[5] if len(test) >= 6 else [] | ||||
|  | ||||
|     test_output_indices = test[6] if len(test) >= 7 else None | ||||
|     output_process_fn = test[6] if len(test) >= 7 else lambda x: x | ||||
|  | ||||
|     for dim_perm in product([-1, 1], repeat=len(dim_args_idx)): | ||||
|         test_name = basic_test_name | ||||
| @ -3039,7 +3058,7 @@ for test in method_tests: | ||||
|         # for-loop bodies don't define scopes, so we have to save the variables | ||||
|         # we want to close over in some way | ||||
|         def do_test(self, name=name, self_size=self_size, args=new_args, test_name=test_name, | ||||
|                     test_output_indices=test_output_indices): | ||||
|                     output_process_fn=output_process_fn): | ||||
|             def check(name): | ||||
|                 is_magic_method = name[:2] == '__' and name[-2:] == '__' | ||||
|                 is_inplace = name[-1] == "_" and not is_magic_method | ||||
| @ -3061,10 +3080,7 @@ for test in method_tests: | ||||
|  | ||||
|                 def fn(*inputs): | ||||
|                     output = getattr(inputs[0], name)(*inputs[1:]) | ||||
|                     if test_output_indices is None: | ||||
|                         return output | ||||
|                     else: | ||||
|                         return tuple(output[i] for i in test_output_indices) | ||||
|                     return output_process_fn(output) | ||||
|  | ||||
|                 if not is_inplace and name not in EXCLUDE_GRADCHECK: | ||||
|                     run_grad_and_gradgrad_checks(self, name, test_name, fn, | ||||
| @ -3074,10 +3090,7 @@ for test in method_tests: | ||||
|                 if hasattr(torch, name) and name not in EXCLUDE_FUNCTIONAL: | ||||
|                     def fn(*inputs): | ||||
|                         output = getattr(torch, name)(*inputs) | ||||
|                         if test_output_indices is None: | ||||
|                             return output | ||||
|                         else: | ||||
|                             return tuple(output[i] for i in test_output_indices) | ||||
|                         return output_process_fn(output) | ||||
|  | ||||
|                     f_args_variable = (self_variable,) + args_variable | ||||
|                     f_args_tensor = (self_tensor,) + args_tensor | ||||
|  | ||||
| @ -1370,22 +1370,11 @@ class TestCuda(TestCase): | ||||
|             # test setitem | ||||
|             x_clone1 = x.clone() | ||||
|             x_clone2 = x.clone() | ||||
|             x_clone3 = x.clone() | ||||
|             first_shape = x[:, ia, None, ib, 0].shape | ||||
|             second_shape = x[ia].shape | ||||
|             x_clone1[:, ia, None, ib, 0] = torch.randn(first_shape).to(x_clone1) | ||||
|             x_clone2[ia] = torch.randn(second_shape).to(x_clone2) | ||||
|  | ||||
|             # fill equivalents | ||||
|             x_clone1[:, ia, None, ib, 0] = 5 | ||||
|             x_clone2[ia] = 7 | ||||
|  | ||||
|             # mask equivalents | ||||
|             mask = (torch.randn(x_clone3.size()) < 0).to(ia.device) | ||||
|             x_clone3[mask] | ||||
|             self.assertEqual(x_clone3[mask].cpu(), x_clone3.cpu()[mask.cpu()]) | ||||
|             x_clone3[mask] = 6 | ||||
|  | ||||
|         cpu = torch.device('cpu') | ||||
|         for device in ['cuda:0', 'cuda:1'] if torch.cuda.device_count() > 1 else ['cuda']: | ||||
|             # Index cpu tensor with cuda tensor | ||||
|  | ||||
| @ -1746,6 +1746,35 @@ class TestDistributions(TestCase): | ||||
|             x = Beta(Tensor([1e-6]), Tensor([1e-6])).sample()[0] | ||||
|             self.assertTrue(np.isfinite(x) and x > 0, 'Invalid Beta.sample(): {}'.format(x)) | ||||
|  | ||||
|     def test_independent_shape(self): | ||||
|         for Dist, params in EXAMPLES: | ||||
|             for i, param in enumerate(params): | ||||
|                 base_dist = Dist(**param) | ||||
|                 x = base_dist.sample() | ||||
|                 base_log_prob_shape = base_dist.log_prob(x).shape | ||||
|                 for reinterpreted_batch_ndims in range(len(base_dist.batch_shape) + 1): | ||||
|                     indep_dist = Independent(base_dist, reinterpreted_batch_ndims) | ||||
|                     indep_log_prob_shape = base_log_prob_shape[:len(base_log_prob_shape) - reinterpreted_batch_ndims] | ||||
|                     self.assertEqual(indep_dist.log_prob(x).shape, indep_log_prob_shape) | ||||
|                     self.assertEqual(indep_dist.sample().shape, base_dist.sample().shape) | ||||
|                     self.assertEqual(indep_dist.has_rsample, base_dist.has_rsample) | ||||
|                     if indep_dist.has_rsample: | ||||
|                         self.assertEqual(indep_dist.sample().shape, base_dist.sample().shape) | ||||
|                     if indep_dist.has_enumerate_support: | ||||
|                         self.assertEqual(indep_dist.enumerate_support().shape, base_dist.enumerate_support().shape) | ||||
|                     try: | ||||
|                         self.assertEqual(indep_dist.mean.shape, base_dist.mean.shape) | ||||
|                     except NotImplementedError: | ||||
|                         pass | ||||
|                     try: | ||||
|                         self.assertEqual(indep_dist.variance.shape, base_dist.variance.shape) | ||||
|                     except NotImplementedError: | ||||
|                         pass | ||||
|                     try: | ||||
|                         self.assertEqual(indep_dist.entropy().shape, indep_log_prob_shape) | ||||
|                     except NotImplementedError: | ||||
|                         pass | ||||
|  | ||||
|     def test_cdf_icdf_inverse(self): | ||||
|         # Tests the invertibility property on the distributions | ||||
|         for Dist, params in EXAMPLES: | ||||
|  | ||||
| @ -254,32 +254,6 @@ class TestIndexing(TestCase): | ||||
|             self.assertEqual(x, x[0]) | ||||
|             self.assertEqual(len(w), 1) | ||||
|  | ||||
|     def test_legacy_dispatch(self): | ||||
|         # compare with indexing using index_select / index_fill etc | ||||
|         x = torch.arange(0, 9).view(3, 3) | ||||
|         idx = torch.tensor([0, 2]) | ||||
|         self.assertEqual(x[idx], x.index_select(0, idx)) | ||||
|         self.assertEqual(x[:, idx], x.index_select(1, idx)) | ||||
|  | ||||
|         mask = x > 4 | ||||
|         self.assertEqual(x[mask], x.masked_select(mask)) | ||||
|  | ||||
|         y = x.clone() | ||||
|         yr = x.clone() | ||||
|         y[idx] = 0 | ||||
|         yr.index_fill_(0, idx, 0) | ||||
|         self.assertEqual(y, yr) | ||||
|         y[:, idx] = 2 | ||||
|         yr.index_fill_(1, idx, 2) | ||||
|         self.assertEqual(y, yr) | ||||
|  | ||||
|         mask = x > 4 | ||||
|         y = x.clone() | ||||
|         yr = x.clone() | ||||
|         y[mask] = 10 | ||||
|         yr.masked_fill_(mask, 10) | ||||
|         self.assertEqual(y, yr) | ||||
|  | ||||
|  | ||||
| # The tests below are from NumPy test_indexing.py with some modifications to | ||||
| # make them compatible with PyTorch. It's licensed under the BDS license below: | ||||
|  | ||||
| @ -121,17 +121,16 @@ class TestJit(TestCase): | ||||
|     # index-2 is not implemented in interpreter | ||||
|     @unittest.expectedFailure | ||||
|     def test_index(self): | ||||
|         x = Variable(torch.rand(2, 2, 2), requires_grad=True) | ||||
|         x = Variable(torch.Tensor([0.4]), requires_grad=True) | ||||
|         y = Variable(torch.LongTensor([0]), requires_grad=True) | ||||
|         y2 = Variable(torch.LongTensor([1]), requires_grad=True) | ||||
|  | ||||
|         @torch.jit.compile(nderivs=0) | ||||
|         def fn(x, y, y2): | ||||
|             return x[y, y2] | ||||
|         def fn(x, y): | ||||
|             return x[y] | ||||
|  | ||||
|         z = fn(x, y, y2) | ||||
|         z = fn(x, y) | ||||
|         with self.assertCompiled(fn): | ||||
|             z2 = fn(x, y, y2) | ||||
|             z2 = fn(x, y) | ||||
|         self.assertEqual(z, z2) | ||||
|  | ||||
|     # Backwards tracing was broken for indexing by a constant, | ||||
|  | ||||
| @ -859,20 +859,26 @@ Tensor svd_backward(const std::vector<torch::autograd::Variable> &grads, const T | ||||
|   auto m = self.size(0); | ||||
|   auto n = self.size(1); | ||||
|   auto k = sigma.size(0); | ||||
|   auto gsigma = grads[1]; | ||||
|  | ||||
|   auto u = raw_u; | ||||
|   auto v = raw_v; | ||||
|   auto gu = grads[0]; | ||||
|   auto gv = grads[2]; | ||||
|  | ||||
|   Tensor u, v; | ||||
|   if (!some) { | ||||
|     // ignore the free subspace | ||||
|     // We ignore the free subspace here because possible base vectors cancel | ||||
|     // each other, e.g., both -v and +v are valid base for a dimension. | ||||
|     // Don't assume behavior of any particular implementation of svd. | ||||
|     u = raw_u.narrow(1, 0, k); | ||||
|     v = raw_v.narrow(1, 0, k); | ||||
|   } else { | ||||
|     u = raw_u; | ||||
|     v = raw_v; | ||||
|     if (gu.defined()) { | ||||
|       gu = gu.narrow(1, 0, k); | ||||
|     } | ||||
|     if (gv.defined()) { | ||||
|       gv = gv.narrow(1, 0, k); | ||||
|     } | ||||
|   } | ||||
|  | ||||
|   auto gu = grads[0]; | ||||
|   auto gsigma = grads[1]; | ||||
|   auto gv = grads[2]; | ||||
|   auto vt = v.t(); | ||||
|  | ||||
|   Tensor sigma_term; | ||||
|  | ||||
| @ -284,12 +284,4 @@ if [ -d "$INSTALL_DIR/bin/" ]; then | ||||
|     cp "$INSTALL_DIR/bin/"/* . | ||||
| fi | ||||
|  | ||||
| # this is for binary builds | ||||
| if [[ $PYTORCH_BINARY_BUILD && $PYTORCH_SO_DEPS ]] | ||||
| then | ||||
|     echo "Copying over dependency libraries $PYTORCH_SO_DEPS" | ||||
|     # copy over dependency libraries into the current dir | ||||
|     cp "$PYTORCH_SO_DEPS" . | ||||
| fi | ||||
|  | ||||
| popd | ||||
|  | ||||
| @ -129,21 +129,22 @@ def is_storage(obj): | ||||
|  | ||||
|  | ||||
| def set_default_tensor_type(t): | ||||
|     r"""Sets the default ``torch.Tensor`` type to type :attr:`t`. | ||||
|     r"""Sets the default ``torch.Tensor`` type to floating point tensor type | ||||
|     :attr:`t`. This type will also be used as default floating point type for | ||||
|     type inference in :func:`torch.tensor`. | ||||
|  | ||||
|     The default tensor type is initially ``"torch.FloatTensor"``. | ||||
|     The default floating point tensor type is initially ``torch.FloatTensor``. | ||||
|  | ||||
|     Args: | ||||
|         t (type or string): the tensor type or its name | ||||
|         t (type or string): the floating point tensor type or its name | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> torch.set_default_tensor_type("torch.FloatTensor") | ||||
|         >>> torch.Tensor([1.2, 3]) | ||||
|  | ||||
|          1.2000 | ||||
|          3.0000 | ||||
|         [torch.FloatTensor of size (2,)] | ||||
|         >>> torch.tensor([1.2, 3]).dtype    # initial default for floating point is torch.float32 | ||||
|         torch.float32 | ||||
|         >>> torch.set_default_tensor_type(torch.DoubleTensor) | ||||
|         >>> torch.tensor([1.2, 3]).dtype    # a new floating point tensor | ||||
|         torch.float64 | ||||
|  | ||||
|     """ | ||||
|     if isinstance(t, _string_classes): | ||||
| @ -152,19 +153,22 @@ def set_default_tensor_type(t): | ||||
|  | ||||
|  | ||||
| def set_default_dtype(d): | ||||
|     r"""Sets the default ``torch.dtype`` type to type :attr:`d`. | ||||
|     r"""Sets the default floating point dtype to :attr:`d`. This type will be | ||||
|     used as default floating point type for type inference in | ||||
|     :func:`torch.tensor`. | ||||
|  | ||||
|     The default floating point dtype is initially ``torch.float32``. | ||||
|  | ||||
|     Args: | ||||
|         d (dtype): the dtype to make the default | ||||
|         d (:class:`torch.dtype`): the floating point dtype to make the default | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> torch.set_default_tensor_type(torch.double) | ||||
|         >>> torch.tensor([1.2, 3], device='cpu') | ||||
|  | ||||
|          1.2000 | ||||
|          3.0000 | ||||
|         [torch.DoubleTensor of size (2,)] | ||||
|         >>> torch.tensor([1.2, 3]).dtype           # initial default for floating point is torch.float32 | ||||
|         torch.float32 | ||||
|         >>> torch.set_default_dtype(torch.float64) | ||||
|         >>> torch.tensor([1.2, 3]).dtype           # a new floating point tensor | ||||
|         torch.float64 | ||||
|  | ||||
|     """ | ||||
|     _C._set_default_dtype(d) | ||||
|  | ||||
| @ -2,11 +2,148 @@ | ||||
|  | ||||
| import torch._C | ||||
| from torch._C import _add_docstr as add_docstr | ||||
| from ._torch_docs import parse_kwargs | ||||
|  | ||||
|  | ||||
| def add_docstr_all(method, docstr): | ||||
|     add_docstr(getattr(torch._C._TensorBase, method), docstr) | ||||
|  | ||||
| new_common_args = parse_kwargs(""" | ||||
|     size (int...): a list, tuple, or :class:`torch.Size` of integers defining the | ||||
|         shape of the output tensor. | ||||
|     dtype (:class:`torch.dtype`, optional): the desired type of returned tensor. | ||||
|         Default: if None, same :class:`torch.dtype` as this tensor. | ||||
|     device (:class:`torch.device`, optional): the desired device of returned tensor. | ||||
|         Default: if None, same :class:`torch.device` as this tensor. | ||||
|     requires_grad (bool, optional): If autograd should record operations on the | ||||
|         returned tensor. Default: ``False``. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('new_tensor', | ||||
|                r""" | ||||
| new_tensor(data, dtype=None, device=None, requires_grad=False) -> Tensor | ||||
|  | ||||
| Returns a new Tensor with :attr:`data` as the tensor data. | ||||
| By default, the returned Tensor has the same :class:`torch.dtype` and | ||||
| :class:`torch.device` as this tensor. | ||||
|  | ||||
| .. warning:: | ||||
|  | ||||
|     :func:`new_tensor` always copies :attr:`data`. If you have a Tensor | ||||
|     ``data`` and want to avoid a copy, use :func:`torch.Tensor.requires_grad_` | ||||
|     or :func:`torch.Tensor.detach`. | ||||
|     If you have a numpy array and want to avoid a copy, use | ||||
|     :func:`torch.from_numpy`. | ||||
|  | ||||
| Args: | ||||
|     data (array_like): The returned Tensor copies :attr:`data`. | ||||
|     {dtype} | ||||
|     {device} | ||||
|     {requires_grad} | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> tensor = torch.ones((2,), dtype=torch.int8) | ||||
|     >>> data = [[0, 1], [2, 3]] | ||||
|     >>> tensor.new_tensor(data) | ||||
|     tensor([[ 0,  1], | ||||
|             [ 2,  3]], dtype=torch.int8) | ||||
|  | ||||
| """.format(**new_common_args)) | ||||
|  | ||||
| add_docstr_all('new_full', | ||||
|                r""" | ||||
| new_full(size, fill_value, dtype=None, device=None, requires_grad=False) -> Tensor | ||||
|  | ||||
| Returns a Tensor of size :attr:`size` filled with :attr:`fill_value`. | ||||
| By default, the returned Tensor has the same :class:`torch.dtype` and | ||||
| :class:`torch.device` as this tensor. | ||||
|  | ||||
| Args: | ||||
|     fill_value (scalar): the number to fill the output tensor with. | ||||
|     {dtype} | ||||
|     {device} | ||||
|     {requires_grad} | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> tensor = torch.ones((2,), dtype=torch.float64) | ||||
|     >>> tensor.new_full((3, 4), 3.141592) | ||||
|     tensor([[ 3.1416,  3.1416,  3.1416,  3.1416], | ||||
|             [ 3.1416,  3.1416,  3.1416,  3.1416], | ||||
|             [ 3.1416,  3.1416,  3.1416,  3.1416]], dtype=torch.float64) | ||||
|  | ||||
| """.format(**new_common_args)) | ||||
|  | ||||
| add_docstr_all('new_empty', | ||||
|                r""" | ||||
| new_empty(size, dtype=None, device=None, requires_grad=False) -> Tensor | ||||
|  | ||||
| Returns a Tensor of size :attr:`size` filled with uninitialized data. | ||||
| By default, the returned Tensor has the same :class:`torch.dtype` and | ||||
| :class:`torch.device` as this tensor. | ||||
|  | ||||
| Args: | ||||
|     {dtype} | ||||
|     {device} | ||||
|     {requires_grad} | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> tensor = torch.ones(()) | ||||
|     >>> tensor.new_empty((2, 3)) | ||||
|     tensor([[ 5.8182e-18,  4.5765e-41, -1.0545e+30], | ||||
|             [ 3.0949e-41,  4.4842e-44,  0.0000e+00]]) | ||||
|  | ||||
| """.format(**new_common_args)) | ||||
|  | ||||
| add_docstr_all('new_ones', | ||||
|                r""" | ||||
| new_ones(size, dtype=None, device=None, requires_grad=False) -> Tensor | ||||
|  | ||||
| Returns a Tensor of size :attr:`size` filled with ``1``. | ||||
| By default, the returned Tensor has the same :class:`torch.dtype` and | ||||
| :class:`torch.device` as this tensor. | ||||
|  | ||||
| Args: | ||||
|     size (int...): a list, tuple, or :class:`torch.Size` of integers defining the | ||||
|         shape of the output tensor. | ||||
|     {dtype} | ||||
|     {device} | ||||
|     {requires_grad} | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> tensor = torch.tensor((), dtype=torch.int32) | ||||
|     >>> tensor.new_ones((2, 3)) | ||||
|     tensor([[ 1,  1,  1], | ||||
|             [ 1,  1,  1]], dtype=torch.int32) | ||||
|  | ||||
| """.format(**new_common_args)) | ||||
|  | ||||
| add_docstr_all('new_zeros', | ||||
|                r""" | ||||
| new_zeros(size, dtype=None, device=None, requires_grad=False) -> Tensor | ||||
|  | ||||
| Returns a Tensor of size :attr:`size` filled with ``0``. | ||||
| By default, the returned Tensor has the same :class:`torch.dtype` and | ||||
| :class:`torch.device` as this tensor. | ||||
|  | ||||
| Args: | ||||
|     size (int...): a list, tuple, or :class:`torch.Size` of integers defining the | ||||
|         shape of the output tensor. | ||||
|     {dtype} | ||||
|     {device} | ||||
|     {requires_grad} | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> tensor = torch.tensor((), dtype=torch.float64) | ||||
|     >>> tensor.new_ones((2, 3)) | ||||
|     tensor([[ 1.,  1.,  1.], | ||||
|             [ 1.,  1.,  1.]], dtype=torch.float64) | ||||
|  | ||||
| """.format(**new_common_args)) | ||||
|  | ||||
| add_docstr_all('abs', | ||||
|                r""" | ||||
| @ -448,9 +585,9 @@ Returns the size in bytes of an individual element. | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> torch.FloatTensor().element_size() | ||||
|     >>> torch.tensor([]).element_size() | ||||
|     4 | ||||
|     >>> torch.ByteTensor().element_size() | ||||
|     >>> torch.tensor([], dtype=torch.uint8).element_size() | ||||
|     1 | ||||
|  | ||||
| """) | ||||
| @ -691,19 +828,15 @@ Args: | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor(5, 3).fill_(1) | ||||
|     >>> t = torch.Tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) | ||||
|     >>> index = torch.LongTensor([0, 4, 2]) | ||||
|     >>> x = torch.ones(5, 3) | ||||
|     >>> t = torch.tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]], dtype=torch.float) | ||||
|     >>> index = torch.tensor([0, 4, 2]) | ||||
|     >>> x.index_add_(0, index, t) | ||||
|     >>> x | ||||
|  | ||||
|       2   3   4 | ||||
|       1   1   1 | ||||
|       8   9  10 | ||||
|       1   1   1 | ||||
|       5   6   7 | ||||
|     [torch.FloatTensor of size (5,3)] | ||||
|  | ||||
|     tensor([[  2.,   3.,   4.], | ||||
|             [  1.,   1.,   1.], | ||||
|             [  8.,   9.,  10.], | ||||
|             [  1.,   1.,   1.], | ||||
|             [  5.,   6.,   7.]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('index_copy_', | ||||
| @ -727,18 +860,14 @@ Args: | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.zeros(5, 3) | ||||
|     >>> t = torch.Tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) | ||||
|     >>> index = torch.LongTensor([0, 4, 2]) | ||||
|     >>> t = torch.tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]], dtype=torch.float) | ||||
|     >>> index = torch.tensor([0, 4, 2]) | ||||
|     >>> x.index_copy_(0, index, t) | ||||
|     >>> x | ||||
|  | ||||
|      1  2  3 | ||||
|      0  0  0 | ||||
|      7  8  9 | ||||
|      0  0  0 | ||||
|      4  5  6 | ||||
|     [torch.FloatTensor of size (5,3)] | ||||
|  | ||||
|     tensor([[ 1.,  2.,  3.], | ||||
|             [ 0.,  0.,  0.], | ||||
|             [ 7.,  8.,  9.], | ||||
|             [ 0.,  0.,  0.], | ||||
|             [ 4.,  5.,  6.]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('index_fill_', | ||||
| @ -754,16 +883,12 @@ Args: | ||||
|     val (float): the value to fill with | ||||
|  | ||||
| Example:: | ||||
|     >>> x = torch.Tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) | ||||
|     >>> index = torch.LongTensor([0, 2]) | ||||
|     >>> x = torch.tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]], dtype=torch.float) | ||||
|     >>> index = torch.tensor([0, 2]) | ||||
|     >>> x.index_fill_(1, index, -1) | ||||
|     >>> x | ||||
|  | ||||
|     -1  2 -1 | ||||
|     -1  5 -1 | ||||
|     -1  8 -1 | ||||
|     [torch.FloatTensor of size (3,3)] | ||||
|  | ||||
|     tensor([[-1.,  2., -1.], | ||||
|             [-1.,  5., -1.], | ||||
|             [-1.,  8., -1.]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('index_put_', | ||||
| @ -819,7 +944,7 @@ This operation is not differentiable. | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor([1.0]) | ||||
|     >>> x = torch.tensor([1.0]) | ||||
|     >>> x.item() | ||||
|     1.0 | ||||
|  | ||||
| @ -1081,20 +1206,14 @@ Args: | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) | ||||
|     >>> x = torch.tensor([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) | ||||
|     >>> x.narrow(0, 0, 2) | ||||
|  | ||||
|      1  2  3 | ||||
|      4  5  6 | ||||
|     [torch.FloatTensor of size (2,3)] | ||||
|  | ||||
|     tensor([[ 1,  2,  3], | ||||
|             [ 4,  5,  6]]) | ||||
|     >>> x.narrow(1, 1, 2) | ||||
|  | ||||
|      2  3 | ||||
|      5  6 | ||||
|      8  9 | ||||
|     [torch.FloatTensor of size (3,2)] | ||||
|  | ||||
|     tensor([[ 2,  3], | ||||
|             [ 5,  6], | ||||
|             [ 8,  9]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('ndimension', | ||||
| @ -1259,13 +1378,11 @@ Args: | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> src = torch.Tensor([[4, 3, 5], | ||||
|     >>> src = torch.tensor([[4, 3, 5], | ||||
|                             [6, 7, 8]]) | ||||
|     >>> src.put_(torch.LongTensor([1, 3]), torch.Tensor([9, 10])) | ||||
|  | ||||
|       4   9   5 | ||||
|      10   7   8 | ||||
|     [torch.FloatTensor of size (2,3)] | ||||
|     >>> src.put_(torch.tensor([1, 3]), torch.tensor([9, 10])) | ||||
|     tensor([[  4,   9,   5], | ||||
|             [ 10,   7,   8]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('qr', | ||||
| @ -1283,8 +1400,8 @@ Fills :attr:`self` tensor with numbers sampled from the discrete uniform | ||||
| distribution over ``[from, to - 1]``. If not specified, the values are usually | ||||
| only bounded by :attr:`self` tensor's data type. However, for floating point | ||||
| types, if unspecified, range will be ``[0, 2^mantissa]`` to ensure that every | ||||
| value is representable. For example, `torch.DoubleTensor(1).random_()` will be | ||||
| uniform in ``[0, 2^53]``. | ||||
| value is representable. For example, `torch.tensor(1, dtype=torch.double).random_()` | ||||
| will be uniform in ``[0, 2^53]``. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('reciprocal', | ||||
| @ -1343,18 +1460,49 @@ Args: | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor([1, 2, 3]) | ||||
|     >>> x = torch.tensor([1, 2, 3]) | ||||
|     >>> x.repeat(4, 2) | ||||
|  | ||||
|      1  2  3  1  2  3 | ||||
|      1  2  3  1  2  3 | ||||
|      1  2  3  1  2  3 | ||||
|      1  2  3  1  2  3 | ||||
|     [torch.FloatTensor of size (4,6)] | ||||
|  | ||||
|     tensor([[ 1,  2,  3,  1,  2,  3], | ||||
|             [ 1,  2,  3,  1,  2,  3], | ||||
|             [ 1,  2,  3,  1,  2,  3], | ||||
|             [ 1,  2,  3,  1,  2,  3]]) | ||||
|     >>> x.repeat(4, 2, 1).size() | ||||
|  | ||||
|     torch.Size([4, 2, 3]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('requires_grad_', | ||||
|                r""" | ||||
| requires_grad_(requires_grad=True) -> Tensor | ||||
|  | ||||
| Change if autograd should record operations on this tensor: sets this tensor's | ||||
| :attr:`requires_grad` attribute in-place. Returns this tensor. | ||||
|  | ||||
| :func:`require_grad_`'s main use case is to tell autograd to begin recording | ||||
| operations on a Tensor ``tensor``. If ``tensor`` has ``requires_grad=False`` | ||||
| (because it was obtained through a DataLoader, or required preprocessing or | ||||
| initialization), ``tensor.requires_grad_()`` makes it so that autograd will | ||||
| begin to record operations on ``tensor``. | ||||
|  | ||||
| Args: | ||||
|     requires_grad (bool): If autograd should record operations on this tensor. | ||||
|         Default: ``True``. | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> # Let's say we want to preprocess some saved weights and use | ||||
|     >>> # the result as new weights. | ||||
|     >>> saved_weights = [0.1, 0.2, 0.3, 0.25] | ||||
|     >>> loaded_weights = torch.tensor(saved_weights) | ||||
|     >>> weights = preprocess(loaded_weights)  # some function | ||||
|     >>> weights | ||||
|     tensor([-0.5503,  0.4926, -2.1158, -0.8303]) | ||||
|  | ||||
|     >>> # Now, start to record operations done to weights | ||||
|     >>> weights.requires_grad_() | ||||
|     >>> out = weights.pow(2).sum() | ||||
|     >>> out.backward() | ||||
|     >>> weights.grad | ||||
|     tensor([-1.1007,  0.9853, -4.2316, -1.6606]) | ||||
|  | ||||
| """) | ||||
|  | ||||
| @ -1386,14 +1534,10 @@ Args: | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor([[1, 2], [3, 4], [5, 6]]) | ||||
|     >>> x = torch.tensor([[1, 2], [3, 4], [5, 6]]) | ||||
|     >>> x.resize_(2, 2) | ||||
|     >>> x | ||||
|  | ||||
|      1  2 | ||||
|      3  4 | ||||
|     [torch.FloatTensor of size (2,2)] | ||||
|  | ||||
|     tensor([[ 1,  2], | ||||
|             [ 3,  4]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('resize_as_', | ||||
| @ -1468,25 +1612,17 @@ Example:: | ||||
|  | ||||
|     >>> x = torch.rand(2, 5) | ||||
|     >>> x | ||||
|     tensor([[ 0.3992,  0.2908,  0.9044,  0.4850,  0.6004], | ||||
|             [ 0.5735,  0.9006,  0.6797,  0.4152,  0.1732]]) | ||||
|     >>> torch.zeros(3, 5).scatter_(0, torch.tensor([[0, 1, 2, 0, 0], [2, 0, 0, 1, 2]]), x) | ||||
|     tensor([[ 0.3992,  0.9006,  0.6797,  0.4850,  0.6004], | ||||
|             [ 0.0000,  0.2908,  0.0000,  0.4152,  0.0000], | ||||
|             [ 0.5735,  0.0000,  0.9044,  0.0000,  0.1732]]) | ||||
|  | ||||
|      0.4319  0.6500  0.4080  0.8760  0.2355 | ||||
|      0.2609  0.4711  0.8486  0.8573  0.1029 | ||||
|     [torch.FloatTensor of size (2,5)] | ||||
|  | ||||
|     >>> torch.zeros(3, 5).scatter_(0, torch.LongTensor([[0, 1, 2, 0, 0], [2, 0, 0, 1, 2]]), x) | ||||
|  | ||||
|      0.4319  0.4711  0.8486  0.8760  0.2355 | ||||
|      0.0000  0.6500  0.0000  0.8573  0.0000 | ||||
|      0.2609  0.0000  0.4080  0.0000  0.1029 | ||||
|     [torch.FloatTensor of size (3,5)] | ||||
|  | ||||
|     >>> z = torch.zeros(2, 4).scatter_(1, torch.LongTensor([[2], [3]]), 1.23) | ||||
|     >>> z = torch.zeros(2, 4).scatter_(1, torch.tensor([[2], [3]]), 1.23) | ||||
|     >>> z | ||||
|  | ||||
|      0.0000  0.0000  1.2300  0.0000 | ||||
|      0.0000  0.0000  0.0000  1.2300 | ||||
|     [torch.FloatTensor of size (2,4)] | ||||
|  | ||||
|     tensor([[ 0.0000,  0.0000,  1.2300,  0.0000], | ||||
|             [ 0.0000,  0.0000,  0.0000,  1.2300]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('select', | ||||
| @ -1591,7 +1727,7 @@ Returns the size of the :attr:`self` tensor. The returned value is a subclass of | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> torch.Tensor(3, 4, 5).size() | ||||
|     >>> torch.empty(3, 4, 5).size() | ||||
|     torch.Size([3, 4, 5]) | ||||
|  | ||||
| """) | ||||
| @ -1654,7 +1790,7 @@ number of storage elements (not bytes). | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor([1, 2, 3, 4, 5]) | ||||
|     >>> x = torch.tensor([1, 2, 3, 4, 5]) | ||||
|     >>> x.storage_offset() | ||||
|     0 | ||||
|     >>> x[3:].storage_offset() | ||||
| @ -1678,7 +1814,7 @@ Args: | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor([[1, 2, 3, 4, 5], [6, 7, 8, 9, 10]]) | ||||
|     >>> x = torch.tensor([[1, 2, 3, 4, 5], [6, 7, 8, 9, 10]]) | ||||
|     >>> x.stride() | ||||
|     (5, 1) | ||||
|     >>>x.stride(0) | ||||
| @ -1744,6 +1880,115 @@ t_() -> Tensor | ||||
| In-place version of :meth:`~Tensor.t` | ||||
| """) | ||||
|  | ||||
| add_docstr_all('to', | ||||
|                r""" | ||||
| to(*args, **kwargs) -> Tensor | ||||
|  | ||||
| Performs Tensor dtype and/or device conversion. A :class:`torch.dtype` and :class:`torch.device` are | ||||
| inferred from the arguments of ``self.to(*args, **kwargs)``. | ||||
|  | ||||
| .. note:: | ||||
|  | ||||
|     If the ``self`` Tensor already | ||||
|     has the correct :class:`torch.dtype` and :class:`torch.device`, then ``self`` is returned. | ||||
|     Otherwise, the returned tensor is a copy of ``self`` with the desired | ||||
|     :class:`torch.dtype` and :class:`torch.device`. | ||||
|  | ||||
| Here are the ways to call ``to``: | ||||
|  | ||||
| .. function:: to(dtype) -> Tensor | ||||
|  | ||||
|     Returns a Tensor with the specified :attr:`dtype` | ||||
|  | ||||
| .. function:: to(device, dtype=None) -> Tensor | ||||
|  | ||||
|     Returns a Tensor with the specified :attr:`device` and (optional) | ||||
|     :attr:`dtype`. If :attr:`dtype` is ``None`` it is inferred to be ``self.dtype``. | ||||
|  | ||||
| .. function:: to(other) -> Tensor | ||||
|  | ||||
|     Returns a Tensor with same :class:`torch.dtype` and :class:`torch.device` as the Tensor | ||||
|     :attr:`other`. | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> tensor = torch.randn(2, 2)  # Initially dtype=float32, device=cpu | ||||
|     >>> tensor.to(torch.float64) | ||||
|     tensor([[-0.5044,  0.0005], | ||||
|             [ 0.3310, -0.0584]], dtype=torch.float64) | ||||
|  | ||||
|     >>> cuda0 = torch.device('cuda:0') | ||||
|     >>> tensor.to(cuda0) | ||||
|     tensor([[-0.5044,  0.0005], | ||||
|             [ 0.3310, -0.0584]], device='cuda:0') | ||||
|  | ||||
|     >>> tensor.to(cuda0, dtype=torch.float64) | ||||
|     tensor([[-0.5044,  0.0005], | ||||
|             [ 0.3310, -0.0584]], dtype=torch.float64, device='cuda:0') | ||||
|  | ||||
|     >>> other = torch.randn((), dtype=torch.float64, device=cuda0) | ||||
|     >>> tensor.to(other) | ||||
|     tensor([[-0.5044,  0.0005], | ||||
|             [ 0.3310, -0.0584]], dtype=torch.float64, device='cuda:0') | ||||
|  | ||||
| """) | ||||
|  | ||||
| add_docstr_all('byte', | ||||
|                r""" | ||||
| byte() -> Tensor | ||||
|  | ||||
| ``self.byte()`` is equivalent to ``self.to(torch.uint8)``. See :func:`to`. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('char', | ||||
|                r""" | ||||
| char() -> Tensor | ||||
|  | ||||
| ``self.char()`` is equivalent to ``self.to(torch.int8)``. See :func:`to`. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('double', | ||||
|                r""" | ||||
| double() -> Tensor | ||||
|  | ||||
| ``self.double()`` is equivalent to ``self.to(torch.float64)``. See :func:`to`. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('float', | ||||
|                r""" | ||||
| float() -> Tensor | ||||
|  | ||||
| ``self.float()`` is equivalent to ``self.to(torch.float32)``. See :func:`to`. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('half', | ||||
|                r""" | ||||
| half() -> Tensor | ||||
|  | ||||
| ``self.half()`` is equivalent to ``self.to(torch.float16)``. See :func:`to`. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('int', | ||||
|                r""" | ||||
| int() -> Tensor | ||||
|  | ||||
| ``self.int()`` is equivalent to ``self.to(torch.int32)``. See :func:`to`. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('long', | ||||
|                r""" | ||||
| long() -> Tensor | ||||
|  | ||||
| ``self.long()`` is equivalent to ``self.to(torch.int64)``. See :func:`to`. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('short', | ||||
|                r""" | ||||
| short() -> Tensor | ||||
|  | ||||
| ``self.short()`` is equivalent to ``self.to(torch.int16)``. See :func:`to`. | ||||
| """) | ||||
|  | ||||
| add_docstr_all('take', | ||||
|                r""" | ||||
| take(indices) -> Tensor | ||||
| @ -1907,33 +2152,18 @@ Example:: | ||||
|  | ||||
|     >>> x = torch.arange(1, 8) | ||||
|     >>> x | ||||
|  | ||||
|      1 | ||||
|      2 | ||||
|      3 | ||||
|      4 | ||||
|      5 | ||||
|      6 | ||||
|      7 | ||||
|     [torch.FloatTensor of size (7,)] | ||||
|  | ||||
|     tensor([ 1.,  2.,  3.,  4.,  5.,  6.,  7.]) | ||||
|     >>> x.unfold(0, 2, 1) | ||||
|  | ||||
|      1  2 | ||||
|      2  3 | ||||
|      3  4 | ||||
|      4  5 | ||||
|      5  6 | ||||
|      6  7 | ||||
|     [torch.FloatTensor of size (6,2)] | ||||
|  | ||||
|     tensor([[ 1.,  2.], | ||||
|             [ 2.,  3.], | ||||
|             [ 3.,  4.], | ||||
|             [ 4.,  5.], | ||||
|             [ 5.,  6.], | ||||
|             [ 6.,  7.]]) | ||||
|     >>> x.unfold(0, 2, 2) | ||||
|  | ||||
|      1  2 | ||||
|      3  4 | ||||
|      5  6 | ||||
|     [torch.FloatTensor of size (3,2)] | ||||
|  | ||||
|     tensor([[ 1.,  2.], | ||||
|             [ 3.,  4.], | ||||
|             [ 5.,  6.]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('uniform_', | ||||
| @ -2031,23 +2261,17 @@ Args: | ||||
|  | ||||
| Example:: | ||||
|  | ||||
|     >>> x = torch.Tensor([[1], [2], [3]]) | ||||
|     >>> x = torch.tensor([[1], [2], [3]]) | ||||
|     >>> x.size() | ||||
|     torch.Size([3, 1]) | ||||
|     >>> x.expand(3, 4) | ||||
|  | ||||
|      1  1  1  1 | ||||
|      2  2  2  2 | ||||
|      3  3  3  3 | ||||
|     [torch.FloatTensor of size (3,4)] | ||||
|  | ||||
|     tensor([[ 1,  1,  1,  1], | ||||
|             [ 2,  2,  2,  2], | ||||
|             [ 3,  3,  3,  3]]) | ||||
|     >>> x.expand(-1, 4)   # -1 means not changing the size of that dimension | ||||
|  | ||||
|      1  1  1  1 | ||||
|      2  2  2  2 | ||||
|      3  3  3  3 | ||||
|     [torch.FloatTensor of size (3,4)] | ||||
|  | ||||
|     tensor([[ 1,  1,  1,  1], | ||||
|             [ 2,  2,  2,  2], | ||||
|             [ 3,  3,  3,  3]]) | ||||
| """) | ||||
|  | ||||
| add_docstr_all('zero_', | ||||
|  | ||||
| @ -73,7 +73,7 @@ def _get_min_log_scale(): | ||||
|  | ||||
|  | ||||
| def _number_format(tensor, min_sz=-1): | ||||
|     int_mode = not tensor.dtype.is_floating_point | ||||
|     floating_dtype = tensor.dtype.is_floating_point  # save this because we cast later | ||||
|     _min_log_scale = _get_min_log_scale() | ||||
|     min_sz = max(min_sz, 2) | ||||
|     tensor = torch.DoubleTensor(tensor.size()).copy_(tensor).abs_().view(tensor.nelement()) | ||||
| @ -90,6 +90,13 @@ def _number_format(tensor, min_sz=-1): | ||||
|     if invalid_value_mask.any(): | ||||
|         min_sz = max(min_sz, 3) | ||||
|  | ||||
|     int_mode = True | ||||
|     # TODO: use fmod? | ||||
|     for value in tensor: | ||||
|         if value != math.ceil(value.item()): | ||||
|             int_mode = False | ||||
|             break | ||||
|  | ||||
|     exp_min = tensor.min() | ||||
|     if exp_min != 0: | ||||
|         exp_min = math.floor(math.log10(exp_min)) + 1 | ||||
| @ -100,6 +107,7 @@ def _number_format(tensor, min_sz=-1): | ||||
|         exp_max = math.floor(math.log10(exp_max)) + 1 | ||||
|     else: | ||||
|         exp_max = 1 | ||||
|     include_decimal_int_mode = floating_dtype and int_mode | ||||
|  | ||||
|     scale = 1 | ||||
|     exp_max = int(exp_max) | ||||
| @ -111,6 +119,9 @@ def _number_format(tensor, min_sz=-1): | ||||
|         else: | ||||
|             sz = max(min_sz, exp_max + 1) | ||||
|             format = '{:' + str(sz) + '.0f}' | ||||
|             if include_decimal_int_mode: | ||||
|                 format += '.' | ||||
|                 sz += 1 | ||||
|     else: | ||||
|         if exp_max - exp_min > prec: | ||||
|             sz = 7 + prec | ||||
| @ -179,7 +190,7 @@ def _tensor_str(self, indent, fmt, scale, sz, summarize): | ||||
| def _str(self): | ||||
|     if self.is_sparse: | ||||
|         size_str = str(tuple(self.shape)).replace(' ', '') | ||||
|         return '{} of size {} with indices:\n{}and values:\n{}'.format( | ||||
|         return '{} of size {} with indices:\n{}\nand values:\n{}'.format( | ||||
|             self.type(), size_str, self._indices(), self._values()) | ||||
|  | ||||
|     prefix = 'tensor(' | ||||
| @ -194,12 +205,16 @@ def _str(self): | ||||
|         if self.device.type == 'cpu' or torch.cuda.current_device() != self.device.index: | ||||
|             suffix = ', device=\'' + str(self.device) + '\'' + suffix | ||||
|  | ||||
|     if self.dtype != torch.get_default_dtype() and self.dtype != torch.int64: | ||||
|         suffix = ', dtype=' + str(self.dtype) + suffix | ||||
|  | ||||
|     if self.numel() == 0: | ||||
|         # In an empty tensor, there are no elements to infer if the dtype should be int64, | ||||
|         # so it must be shown explicitly. | ||||
|         if self.dtype != torch.get_default_dtype(): | ||||
|             suffix = ', dtype=' + str(self.dtype) + suffix | ||||
|         tensor_str = '[]' | ||||
|     else: | ||||
|         if self.dtype != torch.get_default_dtype() and self.dtype != torch.int64: | ||||
|             suffix = ', dtype=' + str(self.dtype) + suffix | ||||
|  | ||||
|         fmt, scale, sz = _number_format(self) | ||||
|         if scale != 1: | ||||
|             prefix = prefix + SCALE_FORMAT.format(scale) + ' ' * indent | ||||
|  | ||||
							
								
								
									
										2977
									
								
								torch/_torch_docs.py
									
									
									
									
									
								
							
							
						
						
									
										2977
									
								
								torch/_torch_docs.py
									
									
									
									
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							| @ -16,6 +16,7 @@ void InputBuffer::add(size_t pos, Variable var) { | ||||
|   if (!old_var.defined()) { | ||||
|     buffer[pos] = std::move(var); | ||||
|   } else { | ||||
|     AutoGPU auto_gpu(var); | ||||
|     // ATen doesn't route sparse additions correctly... | ||||
|     if (old_var.type().is_sparse()) { | ||||
|       buffer[pos] = var + old_var; | ||||
|  | ||||
| @ -9,8 +9,8 @@ | ||||
| #include "torch/csrc/autograd/variable.h" | ||||
| #include "torch/csrc/utils/python_compat.h" | ||||
| #include "torch/csrc/utils/python_numbers.h" | ||||
| #include "torch/csrc/utils/tensor_conversion_dispatch.h" | ||||
| #include "torch/csrc/utils/tensor_new.h" | ||||
| #include "torch/csrc/utils/tensor_conversion_dispatch.h" | ||||
|  | ||||
| #include <ATen/ExpandUtils.h> | ||||
| #include <vector> | ||||
| @ -169,16 +169,6 @@ static Variable applySlicing(const Variable& self, PyObject* index, variable_lis | ||||
|   return result; | ||||
| } | ||||
|  | ||||
| static Tensor typeConvertIndex(const Variable& self, const Variable& ind) { | ||||
|   int64_t device = self.is_cuda() ? self.get_device() : -1; | ||||
|   if (ind.defined()) { | ||||
|     auto& new_type = ind.type().toBackend(self.type().backend()); | ||||
|     return torch::utils::dispatch_type_conversion(ind, new_type, device, false); | ||||
|   } else { | ||||
|     return ind; | ||||
|   } | ||||
| } | ||||
|  | ||||
| static std::vector<Tensor> typeConvertIndices(const Variable& self, const variable_list& indices) { | ||||
|   std::vector<Tensor> converted_inds(indices.size()); | ||||
|   int64_t device = self.is_cuda() ? self.get_device() : -1; | ||||
| @ -271,97 +261,6 @@ static PyObject* applyBoolGetitem(const Variable& self, bool index) { | ||||
|   } | ||||
| } | ||||
|  | ||||
| enum class LegacyIndexingType { | ||||
|   None, | ||||
|   Mask, | ||||
|   Index, | ||||
| }; | ||||
|  | ||||
| static std::pair<LegacyIndexingType, int64_t> | ||||
| getLegacyIndexingType(const Variable& self, const variable_list& vars) { | ||||
|   // TODO: this could be that the broadcasted size is the same. | ||||
|   if (vars.size() == 1 && vars[0].type().scalarType() == ScalarType::Byte && vars[0].is_same_size(self)) { | ||||
|     return std::make_pair(LegacyIndexingType::Mask, -1); | ||||
|   } | ||||
|  | ||||
|   // single tensor indexing | ||||
|   int num_defined_variables = 0; | ||||
|   int64_t index_dim = -1; | ||||
|   for (size_t i = 0; i < vars.size(); i++) { | ||||
|     auto& variable = vars[i]; | ||||
|     auto is_defined = variable.defined(); | ||||
|     num_defined_variables += is_defined; | ||||
|     if (is_defined) { | ||||
|       index_dim = (int64_t)i; | ||||
|       if (num_defined_variables > 1) { | ||||
|         break; | ||||
|       } | ||||
|       if (variable.dim() != 1 || variable.type().scalarType() != ScalarType::Long || variable.numel() == 0) { | ||||
|         num_defined_variables = -1; | ||||
|         break; | ||||
|       } | ||||
|     } | ||||
|   } | ||||
|  | ||||
|   if (num_defined_variables == 1) { | ||||
|     return std::make_pair(LegacyIndexingType::Index, index_dim); | ||||
|   } | ||||
|   // advanced indexing | ||||
|   return std::make_pair(LegacyIndexingType::None, -1); | ||||
| } | ||||
|  | ||||
| static Variable dispatch_legacy_index(const Variable& self, const variable_list& vars, | ||||
|                                       std::pair<LegacyIndexingType, int64_t> legacyIndex) { | ||||
|   LegacyIndexingType indexingType = std::get<0>(legacyIndex); | ||||
|   switch(indexingType) { | ||||
|     case LegacyIndexingType::Mask: { | ||||
|       auto mask = vars[0]; | ||||
|       auto mask_convert = typeConvertIndex(self, mask); | ||||
|       AutoNoGIL no_gil; | ||||
|       AutoGPU auto_gpu(self); | ||||
|       return self.masked_select(mask_convert); | ||||
|     } | ||||
|     case LegacyIndexingType::Index: { | ||||
|       int64_t index_dim = std::get<1>(legacyIndex); | ||||
|       auto index = vars[index_dim]; | ||||
|       auto index_convert = typeConvertIndex(self, index); | ||||
|       AutoNoGIL no_gil; | ||||
|       AutoGPU auto_gpu(self); | ||||
|       return self.index_select(index_dim, index_convert); | ||||
|     } | ||||
|     case LegacyIndexingType::None: | ||||
|     default: { | ||||
|       throw std::runtime_error("Unexpected indexing type"); | ||||
|     } | ||||
|   } | ||||
| } | ||||
|  | ||||
| static Variable dispatch_legacy_index_put_(Variable& self, const variable_list& vars, const Variable& value, | ||||
|                                            std::pair<LegacyIndexingType, int64_t> legacyIndex) { | ||||
|   LegacyIndexingType indexingType = std::get<0>(legacyIndex); | ||||
|   switch(indexingType) { | ||||
|     case LegacyIndexingType::Mask: { | ||||
|       auto mask = vars[0]; | ||||
|       auto mask_convert = typeConvertIndex(self, mask); | ||||
|       AutoNoGIL no_gil; | ||||
|       AutoGPU auto_gpu(self); | ||||
|       return self.masked_fill_(mask_convert, value); | ||||
|     } | ||||
|     case LegacyIndexingType::Index: { | ||||
|       int64_t index_dim = std::get<1>(legacyIndex); | ||||
|       auto index = vars[index_dim]; | ||||
|       auto index_convert = typeConvertIndex(self, index); | ||||
|       AutoNoGIL no_gil; | ||||
|       AutoGPU auto_gpu(self); | ||||
|       return self.index_fill_(index_dim, index_convert, value); | ||||
|     } | ||||
|     case LegacyIndexingType::None: | ||||
|     default: { | ||||
|       throw std::runtime_error("Unexpected indexing type"); | ||||
|     } | ||||
|   } | ||||
| } | ||||
|  | ||||
| PyObject* THPVariable_getitem(PyObject* self, PyObject* index) { | ||||
|   HANDLE_TH_ERRORS | ||||
|   auto& self_ = reinterpret_cast<THPVariable*>(self)->cdata; | ||||
| @ -396,12 +295,6 @@ PyObject* THPVariable_getitem(PyObject* self, PyObject* index) { | ||||
|     return applyBoolGetitem(self_, variableIndices[0].toCByte()); | ||||
|   } | ||||
|  | ||||
|   // TODO move this to ATen | ||||
|   auto legacy_index = getLegacyIndexingType(sliced, variableIndices); | ||||
|   if (std::get<0>(legacy_index) != LegacyIndexingType::None) { | ||||
|     return wrap(dispatch_legacy_index(sliced, variableIndices, legacy_index)); | ||||
|   } | ||||
|  | ||||
|   // indexing by tensors ("advanced" indexing) | ||||
|   return wrap(dispatch_index(sliced, variableIndices)); | ||||
|   Py_RETURN_NONE; | ||||
| @ -468,16 +361,6 @@ int THPVariable_setitem(PyObject* self, PyObject* index, PyObject* py_value) { | ||||
|     return 0; | ||||
|   } | ||||
|  | ||||
|   // TODO move this to ATen | ||||
|   // we are being overly cautious here and only considering the *_fill_ variants | ||||
|   // (value is a scalar), as there could be broadcasting in the value that could | ||||
|   // happen and is not handled by masked_scatter_ and index_copy_ | ||||
|   auto legacy_index = getLegacyIndexingType(sliced, variableIndices); | ||||
|   if (std::get<0>(legacy_index) != LegacyIndexingType::None && value.dim() == 0) { | ||||
|     dispatch_legacy_index_put_(sliced, variableIndices, value, legacy_index); | ||||
|     return 0; | ||||
|   } | ||||
|  | ||||
|   // indexing by tensors ("advanced" indexing) | ||||
|   dispatch_index_put_(sliced, variableIndices, value); | ||||
|   return 0; | ||||
|  | ||||
| @ -112,7 +112,7 @@ def _check_capability(): | ||||
|             warnings.warn(incorrect_binary_warn % (d, name, 8000, CUDA_VERSION)) | ||||
|         elif CUDA_VERSION < 9000 and major >= 7: | ||||
|             warnings.warn(incorrect_binary_warn % (d, name, 9000, CUDA_VERSION)) | ||||
|         elif capability == (3, 0) or capability == (5, 0) or major < 3: | ||||
|         elif capability == (3, 0) or major < 3: | ||||
|             warnings.warn(old_gpu_warn % (d, name, major, capability[1])) | ||||
|  | ||||
|  | ||||
|  | ||||
| @ -16,7 +16,7 @@ class Bernoulli(ExponentialFamily): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Bernoulli(torch.Tensor([0.3])) | ||||
|         >>> m = Bernoulli(torch.tensor([0.3])) | ||||
|         >>> m.sample()  # 30% chance 1; 70% chance 0 | ||||
|          0.0 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -13,7 +13,7 @@ class Beta(ExponentialFamily): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Beta(torch.Tensor([0.5]), torch.Tensor([0.5])) | ||||
|         >>> m = Beta(torch.tensor([0.5]), torch.tensor([0.5])) | ||||
|         >>> m.sample()  # Beta distributed with concentration concentration1 and concentration0 | ||||
|          0.1046 | ||||
|         [torch.FloatTensor of size 1] | ||||
| @ -50,7 +50,7 @@ class Beta(ExponentialFamily): | ||||
|     def rsample(self, sample_shape=()): | ||||
|         value = self._dirichlet.rsample(sample_shape).select(-1, 0) | ||||
|         if isinstance(value, Number): | ||||
|             value = self._dirichlet.concentration.new([value]) | ||||
|             value = self._dirichlet.concentration.new_tensor(value) | ||||
|         return value | ||||
|  | ||||
|     def log_prob(self, value): | ||||
|  | ||||
| @ -17,7 +17,7 @@ class Binomial(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Binomial(100, torch.Tensor([0 , .2, .8, 1])) | ||||
|         >>> m = Binomial(100, torch.tensor([0 , .2, .8, 1])) | ||||
|         >>> x = m.sample() | ||||
|          0 | ||||
|          22 | ||||
|  | ||||
| @ -27,7 +27,7 @@ class Categorical(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Categorical(torch.Tensor([ 0.25, 0.25, 0.25, 0.25 ])) | ||||
|         >>> m = Categorical(torch.tensor([ 0.25, 0.25, 0.25, 0.25 ])) | ||||
|         >>> m.sample()  # equal probability of 0, 1, 2, 3 | ||||
|          3 | ||||
|         [torch.LongTensor of size 1] | ||||
|  | ||||
| @ -15,7 +15,7 @@ class Cauchy(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Cauchy(torch.Tensor([0.0]), torch.Tensor([1.0])) | ||||
|         >>> m = Cauchy(torch.tensor([0.0]), torch.tensor([1.0])) | ||||
|         >>> m.sample()  # sample from a Cauchy distribution with loc=0 and scale=1 | ||||
|          2.3214 | ||||
|         [torch.FloatTensor of size 1] | ||||
| @ -38,11 +38,11 @@ class Cauchy(Distribution): | ||||
|  | ||||
|     @property | ||||
|     def mean(self): | ||||
|         return self.loc.new([float('nan')]).expand(self._extended_shape()) | ||||
|         return self.loc.new_tensor(float('nan')).expand(self._extended_shape()) | ||||
|  | ||||
|     @property | ||||
|     def variance(self): | ||||
|         return self.loc.new([float('inf')]).expand(self._extended_shape()) | ||||
|         return self.loc.new_tensor(float('inf')).expand(self._extended_shape()) | ||||
|  | ||||
|     def rsample(self, sample_shape=torch.Size()): | ||||
|         shape = self._extended_shape(sample_shape) | ||||
|  | ||||
| @ -9,7 +9,7 @@ class Chi2(Gamma): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Chi2(torch.Tensor([1.0])) | ||||
|         >>> m = Chi2(torch.tensor([1.0])) | ||||
|         >>> m.sample()  # Chi2 distributed with shape df=1 | ||||
|          0.1046 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -42,7 +42,7 @@ class Dirichlet(ExponentialFamily): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Dirichlet(torch.Tensor([0.5, 0.5])) | ||||
|         >>> m = Dirichlet(torch.tensor([0.5, 0.5])) | ||||
|         >>> m.sample()  # Dirichlet distributed with concentrarion concentration | ||||
|          0.1046 | ||||
|          0.8954 | ||||
| @ -77,11 +77,11 @@ class Dirichlet(ExponentialFamily): | ||||
|  | ||||
|     @property | ||||
|     def mean(self): | ||||
|         return self.concentration / self.concentration.sum(-1) | ||||
|         return self.concentration / self.concentration.sum(-1, True) | ||||
|  | ||||
|     @property | ||||
|     def variance(self): | ||||
|         con0 = self.concentration.sum(-1) | ||||
|         con0 = self.concentration.sum(-1, True) | ||||
|         return self.concentration * (con0 - self.concentration) / (con0.pow(2) * (con0 + 1)) | ||||
|  | ||||
|     def entropy(self): | ||||
|  | ||||
| @ -12,7 +12,7 @@ class Exponential(ExponentialFamily): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Exponential(torch.Tensor([1.0])) | ||||
|         >>> m = Exponential(torch.tensor([1.0])) | ||||
|         >>> m.sample()  # Exponential distributed with rate=1 | ||||
|          0.1046 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -13,7 +13,7 @@ class FisherSnedecor(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = FisherSnedecor(torch.Tensor([1.0]), torch.Tensor([2.0])) | ||||
|         >>> m = FisherSnedecor(torch.tensor([1.0]), torch.tensor([2.0])) | ||||
|         >>> m.sample()  # Fisher-Snedecor-distributed with df1=1 and df2=2 | ||||
|          0.2453 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -18,7 +18,7 @@ class Gamma(ExponentialFamily): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Gamma(torch.Tensor([1.0]), torch.Tensor([1.0])) | ||||
|         >>> m = Gamma(torch.tensor([1.0]), torch.tensor([1.0])) | ||||
|         >>> m.sample()  # Gamma distributed with concentration=1 and rate=1 | ||||
|          0.1046 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -17,7 +17,7 @@ class Geometric(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Geometric(torch.Tensor([0.3])) | ||||
|         >>> m = Geometric(torch.tensor([0.3])) | ||||
|         >>> m.sample()  # underlying Bernoulli has 30% chance 1; 70% chance 0 | ||||
|          2 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -16,7 +16,7 @@ class Gumbel(TransformedDistribution): | ||||
|  | ||||
|     Examples:: | ||||
|  | ||||
|         >>> m = Gumbel(torch.Tensor([1.0]), torch.Tensor([2.0])) | ||||
|         >>> m = Gumbel(torch.tensor([1.0]), torch.tensor([2.0])) | ||||
|         >>> m.sample()  # sample from Gumbel distribution with loc=1, scale=2 | ||||
|          1.0124 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -52,6 +52,8 @@ class Independent(Distribution): | ||||
|  | ||||
|     @property | ||||
|     def has_enumerate_support(self): | ||||
|         if self.reinterpreted_batch_ndims > 0: | ||||
|             return False | ||||
|         return self.base_dist.has_enumerate_support | ||||
|  | ||||
|     @constraints.dependent_property | ||||
| @ -70,7 +72,7 @@ class Independent(Distribution): | ||||
|         return self.base_dist.sample(sample_shape) | ||||
|  | ||||
|     def rsample(self, sample_shape=torch.Size()): | ||||
|         return self.base_dist.rsample(self, sample_shape) | ||||
|         return self.base_dist.rsample(sample_shape) | ||||
|  | ||||
|     def log_prob(self, value): | ||||
|         log_prob = self.base_dist.log_prob(value) | ||||
| @ -81,4 +83,6 @@ class Independent(Distribution): | ||||
|         return _sum_rightmost(entropy, self.reinterpreted_batch_ndims) | ||||
|  | ||||
|     def enumerate_support(self): | ||||
|         if self.reinterpreted_batch_ndims > 0: | ||||
|             raise NotImplementedError("Enumeration over cartesian product is not implemented") | ||||
|         return self.base_dist.enumerate_support() | ||||
|  | ||||
| @ -11,7 +11,7 @@ class Laplace(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Laplace(torch.Tensor([0.0]), torch.Tensor([1.0])) | ||||
|         >>> m = Laplace(torch.tensor([0.0]), torch.tensor([1.0])) | ||||
|         >>> m.sample()  # Laplace distributed with loc=0, scale=1 | ||||
|          0.1046 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -14,7 +14,7 @@ class LogNormal(TransformedDistribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = LogNormal(torch.Tensor([0.0]), torch.Tensor([1.0])) | ||||
|         >>> m = LogNormal(torch.tensor([0.0]), torch.tensor([1.0])) | ||||
|         >>> m.sample()  # log-normal distributed with mean=0 and stddev=1 | ||||
|          0.1046 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -14,20 +14,18 @@ class LogisticNormal(TransformedDistribution): | ||||
|         X ~ LogisticNormal(loc, scale) | ||||
|         Y = log(X / (1 - X.cumsum(-1)))[..., :-1] ~ Normal(loc, scale) | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = LogisticNormal(torch.Tensor([0.0] * 3), torch.Tensor([1.0] * 3)) | ||||
|         >>> m.sample()  # logistic-normal distributed with mean=(0, 0, 0) and | ||||
|                         # stddev=(1, 1, 1) of the base Normal distribution | ||||
|          0.4163 | ||||
|          0.1386 | ||||
|          0.3539 | ||||
|          0.0912 | ||||
|         [torch.FloatTensor of size (4,)] | ||||
|  | ||||
|     Args: | ||||
|         loc (float or Tensor): mean of the base distribution | ||||
|         scale (float or Tensor): standard deviation of the base distribution | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> # logistic-normal distributed with mean=(0, 0, 0) and stddev=(1, 1, 1) | ||||
|         >>> # of the base Normal distribution | ||||
|         >>> m = distributions.LogisticNormal(torch.tensor([0.0] * 3), torch.tensor([1.0] * 3)) | ||||
|         >>> m.sample() | ||||
|         tensor([ 0.7653,  0.0341,  0.0579,  0.1427]) | ||||
|  | ||||
|     """ | ||||
|     arg_constraints = {'loc': constraints.real, 'scale': constraints.positive} | ||||
|     support = constraints.simplex | ||||
|  | ||||
| @ -24,7 +24,7 @@ class Multinomial(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Multinomial(100, torch.Tensor([ 1, 1, 1, 1])) | ||||
|         >>> m = Multinomial(100, torch.tensor([ 1, 1, 1, 1])) | ||||
|         >>> x = m.sample()  # equal probability of 0, 1, 2, 3 | ||||
|          21 | ||||
|          24 | ||||
| @ -32,7 +32,7 @@ class Multinomial(Distribution): | ||||
|          25 | ||||
|         [torch.FloatTensor of size 4]] | ||||
|  | ||||
|         >>> Multinomial(probs=torch.Tensor([1, 1, 1, 1])).log_prob(x) | ||||
|         >>> Multinomial(probs=torch.tensor([1, 1, 1, 1])).log_prob(x) | ||||
|         -4.1338 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
|  | ||||
| @ -14,7 +14,7 @@ class Normal(ExponentialFamily): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Normal(torch.Tensor([0.0]), torch.Tensor([1.0])) | ||||
|         >>> m = Normal(torch.tensor([0.0]), torch.tensor([1.0])) | ||||
|         >>> m.sample()  # normally distributed with loc=0 and scale=1 | ||||
|          0.1046 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -18,7 +18,7 @@ class OneHotCategorical(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = OneHotCategorical(torch.Tensor([ 0.25, 0.25, 0.25, 0.25 ])) | ||||
|         >>> m = OneHotCategorical(torch.tensor([ 0.25, 0.25, 0.25, 0.25 ])) | ||||
|         >>> m.sample()  # equal probability of 0, 1, 2, 3 | ||||
|          0 | ||||
|          0 | ||||
|  | ||||
| @ -16,7 +16,7 @@ class Pareto(TransformedDistribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Pareto(torch.Tensor([1.0]), torch.Tensor([1.0])) | ||||
|         >>> m = Pareto(torch.tensor([1.0]), torch.tensor([1.0])) | ||||
|         >>> m.sample()  # sample from a Pareto distribution with scale=1 and alpha=1 | ||||
|          1.5623 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -15,7 +15,7 @@ class Poisson(ExponentialFamily): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Poisson(torch.Tensor([4])) | ||||
|         >>> m = Poisson(torch.tensor([4])) | ||||
|         >>> m.sample() | ||||
|          3 | ||||
|         [torch.LongTensor of size 1] | ||||
|  | ||||
| @ -82,8 +82,8 @@ class RelaxedBernoulli(TransformedDistribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = RelaxedBernoulli(torch.Tensor([2.2]), | ||||
|                                  torch.Tensor([0.1, 0.2, 0.3, 0.99])) | ||||
|         >>> m = RelaxedBernoulli(torch.tensor([2.2]), | ||||
|                                  torch.tensor([0.1, 0.2, 0.3, 0.99])) | ||||
|         >>> m.sample() | ||||
|          0.2951 | ||||
|          0.3442 | ||||
|  | ||||
| @ -80,8 +80,8 @@ class RelaxedOneHotCategorical(TransformedDistribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = RelaxedOneHotCategorical(torch.Tensor([2.2]), | ||||
|                                          torch.Tensor([0.1, 0.2, 0.3, 0.4])) | ||||
|         >>> m = RelaxedOneHotCategorical(torch.tensor([2.2]), | ||||
|                                          torch.tensor([0.1, 0.2, 0.3, 0.4])) | ||||
|         >>> m.sample()  # equal probability of 1, 1, 2, 3 | ||||
|          0.1294 | ||||
|          0.2324 | ||||
|  | ||||
| @ -13,7 +13,7 @@ class StudentT(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = StudentT(torch.Tensor([2.0])) | ||||
|         >>> m = StudentT(torch.tensor([2.0])) | ||||
|         >>> m.sample()  # Student's t-distributed with degrees of freedom=2 | ||||
|          0.1046 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -14,7 +14,7 @@ class Uniform(Distribution): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> m = Uniform(torch.Tensor([0.0]), torch.Tensor([5.0])) | ||||
|         >>> m = Uniform(torch.tensor([0.0]), torch.tensor([5.0])) | ||||
|         >>> m.sample()  # uniformly distributed in the range [0.0, 5.0) | ||||
|          2.3418 | ||||
|         [torch.FloatTensor of size 1] | ||||
|  | ||||
| @ -72,24 +72,17 @@ def btrifact(A, info=None, pivot=True): | ||||
|         >>> A = torch.randn(2, 3, 3) | ||||
|         >>> A_LU, pivots = torch.btrifact(A) | ||||
|         >>> A_LU | ||||
|         tensor([[[ 1.3506,  2.5558, -0.0816], | ||||
|                  [ 0.1684,  1.1551,  0.1940], | ||||
|                  [ 0.1193,  0.6189, -0.5497]], | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|           0.7908 -0.0854  0.1522 | ||||
|           0.2757 -1.2942 -1.3715 | ||||
|          -0.6029  0.3609  0.3210 | ||||
|  | ||||
|         (1 ,.,.) = | ||||
|           0.9091  0.1719  0.7741 | ||||
|           0.1625  0.6720  0.1687 | ||||
|          -0.1927 -0.9420 -0.4891 | ||||
|         [torch.FloatTensor of size (2,3,3)] | ||||
|                 [[ 0.4526,  1.2526, -0.3285], | ||||
|                  [-0.7988,  0.7175, -0.9701], | ||||
|                  [ 0.2634, -0.9255, -0.3459]]]) | ||||
|  | ||||
|         >>> pivots | ||||
|  | ||||
|          2  2  3 | ||||
|          1  3  3 | ||||
|         [torch.IntTensor of size (2,3)] | ||||
|  | ||||
|         tensor([[ 3,  3,  3], | ||||
|                 [ 3,  3,  3]], dtype=torch.int32) | ||||
|     """ | ||||
|     # Overwriting reason: | ||||
|     # `info` is being deprecated in favor of `btrifact_with_info`. This warning | ||||
| @ -124,11 +117,10 @@ def btriunpack(LU_data, LU_pivots, unpack_data=True, unpack_pivots=True): | ||||
|  | ||||
|         >>> A = torch.randn(2, 3, 3) | ||||
|         >>> A_LU, pivots = A.btrifact() | ||||
|         >>> P, a_L, a_U = torch.btriunpack(A_LU, pivots) | ||||
|         >>> P, A_L, A_U = torch.btriunpack(A_LU, pivots) | ||||
|         >>> | ||||
|         >>> # test that (P, A_L, A_U) gives LU factorization | ||||
|         >>> # can recover A from factorization | ||||
|         >>> A_ = torch.bmm(P, torch.bmm(A_L, A_U)) | ||||
|         >>> assert torch.equal(A_, A) == True  # can recover A | ||||
|     """ | ||||
|  | ||||
|     nBatch, sz, _ = LU_data.size() | ||||
| @ -311,11 +303,8 @@ def isnan(tensor): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>> torch.isnan(torch.Tensor([1, float('nan'), 2])) | ||||
|          0 | ||||
|          1 | ||||
|          0 | ||||
|         [torch.ByteTensor of size 3] | ||||
|         >>> torch.isnan(torch.tensor([1, float('nan'), 2])) | ||||
|         tensor([ 0,  1,  0], dtype=torch.uint8) | ||||
|     """ | ||||
|     if not isinstance(tensor, torch.Tensor): | ||||
|         raise ValueError("The argument is not a tensor") | ||||
| @ -344,45 +333,25 @@ def unique(input, sorted=False, return_inverse=False): | ||||
|  | ||||
|     Example:: | ||||
|  | ||||
|         >>>> output = torch.unique(torch.LongTensor([1, 3, 2, 3])) | ||||
|         >>>> output | ||||
|         >>> output = torch.unique(torch.tensor([1, 3, 2, 3], dtype=torch.long)) | ||||
|         >>> output | ||||
|         tensor([ 2,  3,  1]) | ||||
|  | ||||
|          2 | ||||
|          3 | ||||
|          1 | ||||
|         [torch.LongTensor of size (3,)] | ||||
|         >>> output, inverse_indices = torch.unique( | ||||
|                 torch.tensor([1, 3, 2, 3], dtype=torch.long), sorted=True, return_inverse=True) | ||||
|         >>> output | ||||
|         tensor([ 1,  2,  3]) | ||||
|         >>> inverse_indices | ||||
|         tensor([ 0,  2,  1,  2]) | ||||
|  | ||||
|         >>>> output, inverse_indices = torch.unique( | ||||
|                  torch.LongTensor([1, 3, 2, 3]), sorted=True, return_inverse=True) | ||||
|         >>>> output | ||||
|         >>> output, inverse_indices = torch.unique( | ||||
|                 torch.tensor([[1, 3], [2, 3]], dtype=torch.long), sorted=True, return_inverse=True) | ||||
|         >>> output | ||||
|         tensor([ 1,  2,  3]) | ||||
|         >>> inverse_indices | ||||
|         tensor([[ 0,  2], | ||||
|                 [ 1,  2]]) | ||||
|  | ||||
|          1 | ||||
|          2 | ||||
|          3 | ||||
|         [torch.LongTensor of size (3,)] | ||||
|  | ||||
|         >>>> inverse_indices | ||||
|  | ||||
|          0 | ||||
|          2 | ||||
|          1 | ||||
|          2 | ||||
|         [torch.LongTensor of size (4,)] | ||||
|  | ||||
|         >>>> output, inverse_indices = torch.unique( | ||||
|                  torch.LongTensor([[1, 3], [2, 3]]), sorted=True, return_inverse=True) | ||||
|         >>>> output | ||||
|  | ||||
|          1 | ||||
|          2 | ||||
|          3 | ||||
|         [torch.LongTensor of size (3,)] | ||||
|  | ||||
|         >>>> inverse_indices | ||||
|  | ||||
|          0  2 | ||||
|          1  2 | ||||
|         [torch.LongTensor of size (2,2)] | ||||
|     """ | ||||
|     output, inverse_indices = torch._unique( | ||||
|         input, | ||||
| @ -412,19 +381,14 @@ def argmax(input, dim=None, keepdim=False): | ||||
|  | ||||
|         >>> a = torch.randn(4, 4) | ||||
|         >>> a | ||||
|         tensor([[ 1.3398,  0.2663, -0.2686,  0.2450], | ||||
|                 [-0.7401, -0.8805, -0.3402, -1.1936], | ||||
|                 [ 0.4907, -1.3948, -1.0691, -0.3132], | ||||
|                 [-1.6092,  0.5419, -0.2993,  0.3195]]) | ||||
|  | ||||
|          2.3461  0.0056  1.4846  0.3911 | ||||
|         -1.3584 -1.0066  0.0530  1.1754 | ||||
|         -0.7929 -0.3194 -1.4865  0.4020 | ||||
|          0.1101  0.6694  1.3456  0.8235 | ||||
|         [torch.FloatTensor of size (4,4)] | ||||
|  | ||||
|         >>> torch.argmax(a, dim=1) | ||||
|         0 | ||||
|         3 | ||||
|         3 | ||||
|         2 | ||||
|         [torch.LongTensor of size (4,)] | ||||
|         tensor([ 0,  2,  0,  1]) | ||||
|     """ | ||||
|     if dim is None: | ||||
|         return torch._argmax(input.contiguous().view(-1), dim=0, keepdim=False) | ||||
| @ -448,19 +412,14 @@ def argmin(input, dim=None, keepdim=False): | ||||
|  | ||||
|         >>> a = torch.randn(4, 4) | ||||
|         >>> a | ||||
|         tensor([[ 0.1139,  0.2254, -0.1381,  0.3687], | ||||
|                 [ 1.0100, -1.1975, -0.0102, -0.4732], | ||||
|                 [-0.9240,  0.1207, -0.7506, -1.0213], | ||||
|                 [ 1.7809, -1.2960,  0.9384,  0.1438]]) | ||||
|  | ||||
|          2.3461  0.0056  1.4846  0.3911 | ||||
|         -1.3584 -1.0066  0.0530  1.1754 | ||||
|         -0.7929 -0.3194 -1.4865  0.4020 | ||||
|          0.1101  0.6694  1.3456  0.8235 | ||||
|         [torch.FloatTensor of size (4,4)] | ||||
|  | ||||
|         >>> torch.argmin(a, dim=1) | ||||
|          1 | ||||
|          0 | ||||
|          2 | ||||
|          0 | ||||
|         [torch.LongTensor of size (4,)] | ||||
|         tensor([ 2,  1,  3,  1]) | ||||
|     """ | ||||
|     if dim is None: | ||||
|         return torch._argmin(input.contiguous().view(-1), dim=0, keepdim=False) | ||||
|  | ||||
| @ -21,17 +21,6 @@ ELSE () | ||||
|   SET(CMAKE_CXX_STANDARD 11) | ||||
| ENDIF () | ||||
|  | ||||
| IF ($ENV{PYTORCH_BINARY_BUILD}) | ||||
|   MESSAGE(STATUS "PYTORCH_BINARY_BUILD detected. Statically linking libstdc++") | ||||
|   SET(CMAKE_CXX_FLAGS "-static-libstdc++ ${CMAKE_CXX_FLAGS}") | ||||
|  | ||||
|   IF (UNIX AND NOT APPLE) | ||||
|     # hiding statically linked library symbols, this flag is not available for the linker under macOS | ||||
|     SET(CMAKE_CXX_FLAGS "-Wl,--exclude-libs,libstdc++.a ${CMAKE_CXX_FLAGS}") | ||||
|   ENDIF(UNIX AND NOT APPLE) | ||||
|  | ||||
| ENDIF() | ||||
|  | ||||
| ADD_LIBRARY(shm SHARED core.cpp) | ||||
| ADD_EXECUTABLE(torch_shm_manager manager.cpp) | ||||
| INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}) | ||||
|  | ||||
| @ -232,11 +232,9 @@ def avg_pool1d(input, kernel_size, stride=None, padding=0, | ||||
|  | ||||
|     Example:: | ||||
|         >>> # pool of square window of size=3, stride=2 | ||||
|         >>> input = torch.Tensor([[[1,2,3,4,5,6,7]]]) | ||||
|         >>> input = torch.tensor([[[1,2,3,4,5,6,7]]]) | ||||
|         >>> F.avg_pool1d(input, kernel_size=3, stride=2) | ||||
|         (0 ,.,.) = | ||||
|           2  4  6 | ||||
|         [torch.FloatTensor of size (1,1,3)] | ||||
|         tensor([[[ 2.,  4.,  6.]]]) | ||||
|     """ | ||||
|     if input.dim() != 3: | ||||
|         raise ValueError('expected 3D input (got {} dimensions)' | ||||
| @ -1038,38 +1036,30 @@ def embedding(input, weight, padding_idx=None, max_norm=None, norm_type=2, | ||||
|     Examples:: | ||||
|  | ||||
|         >>> # a batch of 2 samples of 4 indices each | ||||
|         >>> input = torch.LongTensor([[1,2,4,5],[4,3,2,9]]) | ||||
|         >>> input = torch.tensor([[1,2,4,5],[4,3,2,9]]) | ||||
|         >>> # an embedding matrix containing 10 tensors of size 3 | ||||
|         >>> embedding_matrix = torch.rand(10, 3) | ||||
|         >>> F.embedding(input, embedding_matrix) | ||||
|         tensor([[[ 0.8490,  0.9625,  0.6753], | ||||
|                  [ 0.9666,  0.7761,  0.6108], | ||||
|                  [ 0.6246,  0.9751,  0.3618], | ||||
|                  [ 0.4161,  0.2419,  0.7383]], | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|          -1.0822  1.2522  0.2434 | ||||
|           0.8393 -0.6062 -0.3348 | ||||
|           0.6597  0.0350  0.0837 | ||||
|           0.5521  0.9447  0.0498 | ||||
|  | ||||
|         (1 ,.,.) = | ||||
|           0.6597  0.0350  0.0837 | ||||
|          -0.1527  0.0877  0.4260 | ||||
|           0.8393 -0.6062 -0.3348 | ||||
|          -0.8738 -0.9054  0.4281 | ||||
|         [torch.FloatTensor of size (2,4,3)] | ||||
|                 [[ 0.6246,  0.9751,  0.3618], | ||||
|                  [ 0.0237,  0.7794,  0.0528], | ||||
|                  [ 0.9666,  0.7761,  0.6108], | ||||
|                  [ 0.3385,  0.8612,  0.1867]]]) | ||||
|  | ||||
|         >>> # example with padding_idx | ||||
|         >>> weights = torch.rand(10, 3) | ||||
|         >>> weights[0, :].zero_() | ||||
|         >>> embedding_matrix = weights | ||||
|         >>> input = torch.LongTensor([[0,2,0,5]]) | ||||
|         >>> input = torch.tensor([[0,2,0,5]]) | ||||
|         >>> F.embedding(input, embedding_matrix, padding_idx=0) | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|           0.0000  0.0000  0.0000 | ||||
|           0.3452  0.4937 -0.9361 | ||||
|           0.0000  0.0000  0.0000 | ||||
|           0.0706 -2.1962 -0.6276 | ||||
|         [torch.FloatTensor of size (1,4,3)] | ||||
|  | ||||
|         tensor([[[ 0.0000,  0.0000,  0.0000], | ||||
|                  [ 0.5609,  0.5384,  0.8720], | ||||
|                  [ 0.0000,  0.0000,  0.0000], | ||||
|                  [ 0.6262,  0.2438,  0.7471]]]) | ||||
|     """ | ||||
|     input = input.contiguous() | ||||
|     if padding_idx is not None: | ||||
| @ -1133,14 +1123,11 @@ def embedding_bag(embedding_matrix, indices, offsets=None, | ||||
|             >>> # an Embedding module containing 10 tensors of size 3 | ||||
|             >>> embedding_matrix = torch.rand(10, 3) | ||||
|             >>> # a batch of 2 samples of 4 indices each | ||||
|             >>> input = torch.LongTensor([1,2,4,5,4,3,2,9]) | ||||
|             >>> offsets = torch.LongTensor([0,4]) | ||||
|             >>> embedding_bag(embedding_matrix, input, offsets) | ||||
|  | ||||
|             -1.1840 -0.2547 -0.5860 | ||||
|             -0.7126  0.0002 -0.3411 | ||||
|             [torch.FloatTensor of size (2,3)] | ||||
|  | ||||
|             >>> input = torch.tensor([1,2,4,5,4,3,2,9]) | ||||
|             >>> offsets = torch.tensor([0,4]) | ||||
|             >>> F.embedding_bag(embedding_matrix, input, offsets) | ||||
|             tensor([[ 0.3397,  0.3552,  0.5545], | ||||
|                     [ 0.5893,  0.4386,  0.5882]]) | ||||
|         """ | ||||
|     if indices.dim() == 2: | ||||
|         if offsets is not None: | ||||
| @ -1328,9 +1315,9 @@ def nll_loss(input, target, weight=None, size_average=True, ignore_index=-100, r | ||||
|     Example:: | ||||
|  | ||||
|         >>> # input is of size N x C = 3 x 5 | ||||
|         >>> input = torch.randn(3, 5) | ||||
|         >>> input = torch.randn(3, 5, requires_grad=True) | ||||
|         >>> # each element in target has to have 0 <= value < C | ||||
|         >>> target = torch.LongTensor([1, 0, 4]) | ||||
|         >>> target = torch.tensor([1, 0, 4]) | ||||
|         >>> output = F.nll_loss(F.log_softmax(input), target) | ||||
|         >>> output.backward() | ||||
|     """ | ||||
| @ -1448,7 +1435,7 @@ def cross_entropy(input, target, weight=None, size_average=True, ignore_index=-1 | ||||
|     Examples:: | ||||
|  | ||||
|         >>> input = torch.randn(3, 5, requires_grad=True) | ||||
|         >>> target = torch.LongTensor(3).random_(5) | ||||
|         >>> target = torch.randint(5, (3,), dtype=torch.int64) | ||||
|         >>> loss = F.cross_entropy(input, target) | ||||
|         >>> loss.backward() | ||||
|     """ | ||||
| @ -1477,8 +1464,8 @@ def binary_cross_entropy(input, target, weight=None, size_average=True, reduce=T | ||||
|  | ||||
|     Examples:: | ||||
|  | ||||
|         >>> input = torch.randn(3, requires_grad=True) | ||||
|         >>> target = torch.LongTensor(3).random_(2) | ||||
|         >>> input = torch.randn((3, 2), requires_grad=True) | ||||
|         >>> target = torch.rand((3, 2), requires_grad=False) | ||||
|         >>> loss = F.binary_cross_entropy(F.sigmoid(input), target) | ||||
|         >>> loss.backward() | ||||
|     """ | ||||
| @ -1519,7 +1506,7 @@ def binary_cross_entropy_with_logits(input, target, weight=None, size_average=Tr | ||||
|     Examples:: | ||||
|  | ||||
|          >>> input = torch.randn(3, requires_grad=True) | ||||
|          >>> target = torch.FloatTensor(3).random_(2) | ||||
|          >>> target = torch.empty(3).random_(2) | ||||
|          >>> loss = F.binary_cross_entropy_with_logits(input, target) | ||||
|          >>> loss.backward() | ||||
|     """ | ||||
| @ -1657,7 +1644,7 @@ def pixel_shuffle(input, upscale_factor): | ||||
|     Examples:: | ||||
|  | ||||
|         >>> ps = nn.PixelShuffle(3) | ||||
|         >>> input = torch.Tensor(1, 9, 4, 4) | ||||
|         >>> input = torch.empty(1, 9, 4, 4) | ||||
|         >>> output = ps(input) | ||||
|         >>> print(output.size()) | ||||
|         torch.Size([1, 1, 12, 12]) | ||||
| @ -1920,7 +1907,7 @@ def pad(input, pad, mode='constant', value=0): | ||||
|  | ||||
|     Examples:: | ||||
|  | ||||
|         >>> t4d = torch.Tensor(3, 3, 4, 2) | ||||
|         >>> t4d = torch.empty(3, 3, 4, 2) | ||||
|         >>> p1d = (1, 1) # pad last dim by 1 on each side | ||||
|         >>> out = F.pad(t4d, p1d, "constant", 0)  # effectively zero padding | ||||
|         >>> print(out.data.size()) | ||||
| @ -1929,7 +1916,7 @@ def pad(input, pad, mode='constant', value=0): | ||||
|         >>> out = F.pad(t4d, p2d, "constant", 0) | ||||
|         >>> print(out.data.size()) | ||||
|         torch.Size([3, 3, 8, 4]) | ||||
|         >>> t4d = torch.Tensor(3, 3, 4, 2) | ||||
|         >>> t4d = torch.empty(3, 3, 4, 2) | ||||
|         >>> p3d = (0, 1, 2, 1, 3, 3) # pad by (0, 1), (2, 1), and (3, 3) | ||||
|         >>> out = F.pad(t4d, p3d, "constant", 0) | ||||
|         >>> print(out.data.size()) | ||||
|  | ||||
| @ -57,7 +57,7 @@ def uniform_(tensor, a=0, b=1): | ||||
|         b: the upper bound of the uniform distribution | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.uniform_(w) | ||||
|     """ | ||||
|     with torch.no_grad(): | ||||
| @ -74,7 +74,7 @@ def normal_(tensor, mean=0, std=1): | ||||
|         std: the standard deviation of the normal distribution | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.normal_(w) | ||||
|     """ | ||||
|     with torch.no_grad(): | ||||
| @ -89,7 +89,7 @@ def constant_(tensor, val): | ||||
|         val: the value to fill the tensor with | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.constant_(w, 0.3) | ||||
|     """ | ||||
|     with torch.no_grad(): | ||||
| @ -105,7 +105,7 @@ def eye_(tensor): | ||||
|         tensor: a 2-dimensional `torch.Tensor` | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.eye_(w) | ||||
|     """ | ||||
|     if tensor.ndimension() != 2: | ||||
| @ -125,7 +125,7 @@ def dirac_(tensor): | ||||
|         tensor: a {3, 4, 5}-dimensional `torch.Tensor` | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 16, 5, 5) | ||||
|         >>> w = torch.empty(3, 16, 5, 5) | ||||
|         >>> nn.init.dirac_(w) | ||||
|     """ | ||||
|     dimensions = tensor.ndimension() | ||||
| @ -184,7 +184,7 @@ def xavier_uniform_(tensor, gain=1): | ||||
|         gain: an optional scaling factor | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.xavier_uniform_(w, gain=nn.init.calculate_gain('relu')) | ||||
|     """ | ||||
|     fan_in, fan_out = _calculate_fan_in_and_fan_out(tensor) | ||||
| @ -211,7 +211,7 @@ def xavier_normal_(tensor, gain=1): | ||||
|         gain: an optional scaling factor | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.xavier_normal_(w) | ||||
|     """ | ||||
|     fan_in, fan_out = _calculate_fan_in_and_fan_out(tensor) | ||||
| @ -254,7 +254,7 @@ def kaiming_uniform_(tensor, a=0, mode='fan_in', nonlinearity='leaky_relu'): | ||||
|             recommended to use only with 'relu' or 'leaky_relu' (default). | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.kaiming_uniform_(w, mode='fan_in', nonlinearity='relu') | ||||
|     """ | ||||
|     fan = _calculate_correct_fan(tensor, mode) | ||||
| @ -289,7 +289,7 @@ def kaiming_normal_(tensor, a=0, mode='fan_in', nonlinearity='leaky_relu'): | ||||
|             recommended to use only with 'relu' or 'leaky_relu' (default). | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.kaiming_normal_(w, mode='fan_out', nonlinearity='relu') | ||||
|     """ | ||||
|     fan = _calculate_correct_fan(tensor, mode) | ||||
| @ -311,7 +311,7 @@ def orthogonal_(tensor, gain=1): | ||||
|         gain: optional scaling factor | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.orthogonal_(w) | ||||
|     """ | ||||
|     if tensor.ndimension() < 2: | ||||
| @ -353,7 +353,7 @@ def sparse_(tensor, sparsity, std=0.01): | ||||
|             the non-zero values | ||||
|  | ||||
|     Examples: | ||||
|         >>> w = torch.Tensor(3, 5) | ||||
|         >>> w = torch.empty(3, 5) | ||||
|         >>> nn.init.sparse_(w, sparsity=0.1) | ||||
|     """ | ||||
|     if tensor.ndimension() != 2: | ||||
|  | ||||
| @ -166,7 +166,7 @@ class NLLLoss(_WeightedLoss): | ||||
|         >>> # input is of size N x C = 3 x 5 | ||||
|         >>> input = torch.randn(3, 5, requires_grad=True) | ||||
|         >>> # each element in target has to have 0 <= value < C | ||||
|         >>> target = torch.LongTensor([1, 0, 4]) | ||||
|         >>> target = torch.tensor([1, 0, 4]) | ||||
|         >>> output = loss(m(input), target) | ||||
|         >>> output.backward() | ||||
|         >>> | ||||
| @ -178,7 +178,7 @@ class NLLLoss(_WeightedLoss): | ||||
|         >>> data = torch.randn(N, 16, 10, 10) | ||||
|         >>> m = nn.Conv2d(16, C, (3, 3)) | ||||
|         >>> # each element in target has to have 0 <= value < C | ||||
|         >>> target = torch.LongTensor(N, 8, 8).random_(0, C) | ||||
|         >>> target = torch.tensor(N, 8, 8).random_(0, C) | ||||
|         >>> output = loss(m(data), target) | ||||
|         >>> output.backward() | ||||
|     """ | ||||
| @ -419,7 +419,7 @@ class BCELoss(_WeightedLoss): | ||||
|         >>> m = nn.Sigmoid() | ||||
|         >>> loss = nn.BCELoss() | ||||
|         >>> input = torch.randn(3, requires_grad=True) | ||||
|         >>> target = torch.FloatTensor(3).random_(2) | ||||
|         >>> target = torch.empty(3).random_(2) | ||||
|         >>> output = loss(m(input), target) | ||||
|         >>> output.backward() | ||||
|     """ | ||||
| @ -480,7 +480,7 @@ class BCEWithLogitsLoss(_Loss): | ||||
|  | ||||
|         >>> loss = nn.BCEWithLogitsLoss() | ||||
|         >>> input = torch.randn(3, requires_grad=True) | ||||
|         >>> target = torch.FloatTensor(3).random_(2) | ||||
|         >>> target = torch.empty(3).random_(2) | ||||
|         >>> output = loss(input, target) | ||||
|         >>> output.backward() | ||||
|     """ | ||||
| @ -744,7 +744,7 @@ class CrossEntropyLoss(_WeightedLoss): | ||||
|  | ||||
|         >>> loss = nn.CrossEntropyLoss() | ||||
|         >>> input = torch.randn(3, 5, requires_grad=True) | ||||
|         >>> target = torch.LongTensor(3).random_(5) | ||||
|         >>> target = torch.empty(3, dtype=torch.long).random_(5) | ||||
|         >>> output = loss(input, target) | ||||
|         >>> output.backward() | ||||
|     """ | ||||
|  | ||||
| @ -211,17 +211,13 @@ class Module(object): | ||||
|             >>> net = nn.Sequential(nn.Linear(2, 2), nn.Linear(2, 2)) | ||||
|             >>> net.apply(init_weights) | ||||
|             Linear(in_features=2, out_features=2, bias=True) | ||||
|  | ||||
|              1  1 | ||||
|              1  1 | ||||
|             [torch.FloatTensor of size (2,2)] | ||||
|  | ||||
|             Parameter containing: | ||||
|             tensor([[ 1.,  1.], | ||||
|                     [ 1.,  1.]]) | ||||
|             Linear(in_features=2, out_features=2, bias=True) | ||||
|  | ||||
|              1  1 | ||||
|              1  1 | ||||
|             [torch.FloatTensor of size (2,2)] | ||||
|  | ||||
|             Parameter containing: | ||||
|             tensor([[ 1.,  1.], | ||||
|                     [ 1.,  1.]]) | ||||
|             Sequential( | ||||
|               (0): Linear(in_features=2, out_features=2, bias=True) | ||||
|               (1): Linear(in_features=2, out_features=2, bias=True) | ||||
| @ -230,7 +226,6 @@ class Module(object): | ||||
|               (0): Linear(in_features=2, out_features=2, bias=True) | ||||
|               (1): Linear(in_features=2, out_features=2, bias=True) | ||||
|             ) | ||||
|  | ||||
|         """ | ||||
|         for module in self.children(): | ||||
|             module.apply(fn) | ||||
|  | ||||
| @ -23,7 +23,7 @@ class PixelShuffle(Module): | ||||
|     Examples:: | ||||
|  | ||||
|         >>> ps = nn.PixelShuffle(3) | ||||
|         >>> input = torch.Tensor(1, 9, 4, 4) | ||||
|         >>> input = torch.tensor(1, 9, 4, 4) | ||||
|         >>> output = ps(input) | ||||
|         >>> print(output.size()) | ||||
|         torch.Size([1, 1, 12, 12]) | ||||
|  | ||||
| @ -256,29 +256,19 @@ class MaxUnpool1d(_MaxUnpoolNd): | ||||
|  | ||||
|         >>> pool = nn.MaxPool1d(2, stride=2, return_indices=True) | ||||
|         >>> unpool = nn.MaxUnpool1d(2, stride=2) | ||||
|         >>> input = torch.Tensor([[[1, 2, 3, 4, 5, 6, 7, 8]]]) | ||||
|         >>> input = torch.tensor([[[1., 2, 3, 4, 5, 6, 7, 8]]]) | ||||
|         >>> output, indices = pool(input) | ||||
|         >>> unpool(output, indices) | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|            0   2   0   4   0   6   0   8 | ||||
|         [torch.FloatTensor of size (1,1,8)] | ||||
|         tensor([[[ 0.,  2.,  0.,  4.,  0.,  6.,  0., 8.]]]) | ||||
|  | ||||
|         >>> # Example showcasing the use of output_size | ||||
|         >>> input = torch.Tensor([[[1, 2, 3, 4, 5, 6, 7, 8, 9]]]) | ||||
|         >>> input = torch.tensor([[[1., 2, 3, 4, 5, 6, 7, 8, 9]]]) | ||||
|         >>> output, indices = pool(input) | ||||
|         >>> unpool(output, indices, output_size=input.size()) | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|            0   2   0   4   0   6   0   8   0 | ||||
|         [torch.FloatTensor of size (1,1,9)] | ||||
|         tensor([[[ 0.,  2.,  0.,  4.,  0.,  6.,  0., 8.,  0.]]]) | ||||
|  | ||||
|         >>> unpool(output, indices) | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|            0   2   0   4   0   6   0   8 | ||||
|         [torch.FloatTensor of size (1,1,8)] | ||||
|  | ||||
|         tensor([[[ 0.,  2.,  0.,  4.,  0.,  6.,  0., 8.]]]) | ||||
|     """ | ||||
|  | ||||
|     def __init__(self, kernel_size, stride=None, padding=0): | ||||
| @ -333,31 +323,24 @@ class MaxUnpool2d(_MaxUnpoolNd): | ||||
|  | ||||
|         >>> pool = nn.MaxPool2d(2, stride=2, return_indices=True) | ||||
|         >>> unpool = nn.MaxUnpool2d(2, stride=2) | ||||
|         >>> input = torch.Tensor([[[[ 1,  2,  3,  4], | ||||
|         >>> input = torch.tensor([[[[ 1.,  2,  3,  4], | ||||
|                                     [ 5,  6,  7,  8], | ||||
|                                     [ 9, 10, 11, 12], | ||||
|                                     [13, 14, 15, 16]]]]) | ||||
|         >>> output, indices = pool(input) | ||||
|         >>> unpool(output, indices) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|            0   0   0   0 | ||||
|            0   6   0   8 | ||||
|            0   0   0   0 | ||||
|            0  14   0  16 | ||||
|         [torch.FloatTensor of size (1,1,4,4)] | ||||
|         tensor([[[[  0.,   0.,   0.,   0.], | ||||
|                   [  0.,   6.,   0.,   8.], | ||||
|                   [  0.,   0.,   0.,   0.], | ||||
|                   [  0.,  14.,   0.,  16.]]]]) | ||||
|  | ||||
|         >>> # specify a different output size than input size | ||||
|         >>> unpool(output, indices, output_size=torch.Size([1, 1, 5, 5])) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|            0   0   0   0   0 | ||||
|            6   0   8   0   0 | ||||
|            0   0   0  14   0 | ||||
|           16   0   0   0   0 | ||||
|            0   0   0   0   0 | ||||
|         [torch.FloatTensor of size (1,1,5,5)] | ||||
|  | ||||
|         tensor([[[[  0.,   0.,   0.,   0.,   0.], | ||||
|                   [  6.,   0.,   8.,   0.,   0.], | ||||
|                   [  0.,   0.,   0.,  14.,   0.], | ||||
|                   [ 16.,   0.,   0.,   0.,   0.], | ||||
|                   [  0.,   0.,   0.,   0.,   0.]]]]) | ||||
|     """ | ||||
|  | ||||
|     def __init__(self, kernel_size, stride=None, padding=0): | ||||
| @ -479,11 +462,8 @@ class AvgPool1d(_AvgPoolNd): | ||||
|  | ||||
|         >>> # pool with window of size=3, stride=2 | ||||
|         >>> m = nn.AvgPool1d(3, stride=2) | ||||
|         >>> m(torch.Tensor([[[1,2,3,4,5,6,7]]])) | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|           2  4  6 | ||||
|         [torch.FloatTensor of size (1,1,3)] | ||||
|         >>> m(torch.tensor([[[1.,2,3,4,5,6,7]]])) | ||||
|         tensor([[[ 2.,  4.,  6.]]]) | ||||
|     """ | ||||
|  | ||||
|     def __init__(self, kernel_size, stride=None, padding=0, ceil_mode=False, | ||||
|  | ||||
| @ -51,32 +51,25 @@ class Embedding(Module): | ||||
|         >>> # a batch of 2 samples of 4 indices each | ||||
|         >>> input = torch.LongTensor([[1,2,4,5],[4,3,2,9]]) | ||||
|         >>> embedding(input) | ||||
|         tensor([[[-0.0251, -1.6902,  0.7172], | ||||
|                  [-0.6431,  0.0748,  0.6969], | ||||
|                  [ 1.4970,  1.3448, -0.9685], | ||||
|                  [-0.3677, -2.7265, -0.1685]], | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|          -1.0822  1.2522  0.2434 | ||||
|           0.8393 -0.6062 -0.3348 | ||||
|           0.6597  0.0350  0.0837 | ||||
|           0.5521  0.9447  0.0498 | ||||
|                 [[ 1.4970,  1.3448, -0.9685], | ||||
|                  [ 0.4362, -0.4004,  0.9400], | ||||
|                  [-0.6431,  0.0748,  0.6969], | ||||
|                  [ 0.9124, -2.3616,  1.1151]]]) | ||||
|  | ||||
|         (1 ,.,.) = | ||||
|           0.6597  0.0350  0.0837 | ||||
|          -0.1527  0.0877  0.4260 | ||||
|           0.8393 -0.6062 -0.3348 | ||||
|          -0.8738 -0.9054  0.4281 | ||||
|         [torch.FloatTensor of size (2,4,3)] | ||||
|  | ||||
|         >>> # example with padding_idx | ||||
|         >>> embedding = nn.Embedding(10, 3, padding_idx=0) | ||||
|         >>> input = torch.LongTensor([[0,2,0,5]]) | ||||
|         >>> embedding(input) | ||||
|  | ||||
|         (0 ,.,.) = | ||||
|           0.0000  0.0000  0.0000 | ||||
|           0.3452  0.4937 -0.9361 | ||||
|           0.0000  0.0000  0.0000 | ||||
|           0.0706 -2.1962 -0.6276 | ||||
|         [torch.FloatTensor of size (1,4,3)] | ||||
|  | ||||
|         tensor([[[ 0.0000,  0.0000,  0.0000], | ||||
|                  [ 0.1535, -2.0309,  0.9315], | ||||
|                  [ 0.0000,  0.0000,  0.0000], | ||||
|                  [-0.1655,  0.9897,  0.0635]]]) | ||||
|     """ | ||||
|  | ||||
|     def __init__(self, num_embeddings, embedding_dim, padding_idx=None, | ||||
| @ -140,15 +133,13 @@ class Embedding(Module): | ||||
|  | ||||
|         Examples:: | ||||
|  | ||||
|             >> # FloatTensor containing pretrained weights | ||||
|             >> weight = torch.FloatTensor([[1, 2.3, 3], [4, 5.1, 6.3]]) | ||||
|             >> embedding = nn.Embedding.from_pretrained(weight) | ||||
|             >> # Get embeddings for index 1 | ||||
|             >> input = torch.LongTensor([1]) | ||||
|             >> embedding(input) | ||||
|  | ||||
|              4.0000  5.1000  6.3000 | ||||
|             [torch.FloatTensor of size (1,3)] | ||||
|             >>> # FloatTensor containing pretrained weights | ||||
|             >>> weight = torch.FloatTensor([[1, 2.3, 3], [4, 5.1, 6.3]]) | ||||
|             >>> embedding = nn.Embedding.from_pretrained(weight) | ||||
|             >>> # Get embeddings for index 1 | ||||
|             >>> input = torch.LongTensor([1]) | ||||
|             >>> embedding(input) | ||||
|             tensor([[ 4.0000,  5.1000,  6.3000]]) | ||||
|         """ | ||||
|         assert embeddings.dim() == 2, \ | ||||
|             'Embeddings parameter is expected to be 2-dimensional' | ||||
| @ -215,11 +206,8 @@ class EmbeddingBag(Module): | ||||
|         >>> input = torch.LongTensor([1,2,4,5,4,3,2,9]) | ||||
|         >>> offsets = torch.LongTensor([0,4]) | ||||
|         >>> embedding_sum(input, offsets) | ||||
|  | ||||
|         -0.7296 -4.6926  0.3295 | ||||
|         -0.5186 -0.5631 -0.2792 | ||||
|         [torch.FloatTensor of size (2,3)] | ||||
|  | ||||
|         tensor([[-0.8861, -5.4350, -0.0523], | ||||
|                 [ 1.1306, -2.5798, -1.0044]]) | ||||
|     """ | ||||
|  | ||||
|     def __init__(self, num_embeddings, embedding_dim, | ||||
|  | ||||
| @ -52,80 +52,60 @@ class Upsample(Module): | ||||
|  | ||||
|         >>> input = torch.arange(1, 5).view(1, 1, 2, 2) | ||||
|         >>> input | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1  2 | ||||
|           3  4 | ||||
|         [torch.FloatTensor of size (1,1,2,2)] | ||||
|         tensor([[[[ 1.,  2.], | ||||
|                   [ 3.,  4.]]]]) | ||||
|  | ||||
|         >>> m = nn.Upsample(scale_factor=2, mode='nearest') | ||||
|         >>> m(input) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1  1  2  2 | ||||
|           1  1  2  2 | ||||
|           3  3  4  4 | ||||
|           3  3  4  4 | ||||
|         [torch.FloatTensor of size (1,1,4,4)] | ||||
|         tensor([[[[ 1.,  1.,  2.,  2.], | ||||
|                   [ 1.,  1.,  2.,  2.], | ||||
|                   [ 3.,  3.,  4.,  4.], | ||||
|                   [ 3.,  3.,  4.,  4.]]]]) | ||||
|  | ||||
|         >>> m = nn.Upsample(scale_factor=2, mode='bilinear')  # align_corners=False | ||||
|         >>> m(input) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1.0000  1.2500  1.7500  2.0000 | ||||
|           1.5000  1.7500  2.2500  2.5000 | ||||
|           2.5000  2.7500  3.2500  3.5000 | ||||
|           3.0000  3.2500  3.7500  4.0000 | ||||
|         [torch.FloatTensor of size (1,1,4,4)] | ||||
|         tensor([[[[ 1.0000,  1.2500,  1.7500,  2.0000], | ||||
|                   [ 1.5000,  1.7500,  2.2500,  2.5000], | ||||
|                   [ 2.5000,  2.7500,  3.2500,  3.5000], | ||||
|                   [ 3.0000,  3.2500,  3.7500,  4.0000]]]]) | ||||
|  | ||||
|         >>> m = nn.Upsample(scale_factor=2, mode='bilinear', align_corners=True) | ||||
|         >>> m(input) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1.0000  1.3333  1.6667  2.0000 | ||||
|           1.6667  2.0000  2.3333  2.6667 | ||||
|           2.3333  2.6667  3.0000  3.3333 | ||||
|           3.0000  3.3333  3.6667  4.0000 | ||||
|         [torch.FloatTensor of size (1,1,4,4)] | ||||
|         tensor([[[[ 1.0000,  1.3333,  1.6667,  2.0000], | ||||
|                   [ 1.6667,  2.0000,  2.3333,  2.6667], | ||||
|                   [ 2.3333,  2.6667,  3.0000,  3.3333], | ||||
|                   [ 3.0000,  3.3333,  3.6667,  4.0000]]]]) | ||||
|  | ||||
|         >>> # Try scaling the same data in a larger tensor | ||||
|         >>> | ||||
|         >>> input_3x3 = torch.zeros(3, 3).view(1, 1, 3, 3) | ||||
|         >>> input_3x3[:, :, :2, :2].copy_(input) | ||||
|         tensor([[[[ 1.,  2.], | ||||
|                   [ 3.,  4.]]]]) | ||||
|         >>> input_3x3 | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1  2  0 | ||||
|           3  4  0 | ||||
|           0  0  0 | ||||
|         [torch.FloatTensor of size (1,1,3,3)] | ||||
|         tensor([[[[ 1.,  2.,  0.], | ||||
|                   [ 3.,  4.,  0.], | ||||
|                   [ 0.,  0.,  0.]]]]) | ||||
|  | ||||
|         >>> m = nn.Upsample(scale_factor=2, mode='bilinear')  # align_corners=False | ||||
|         >>> # Notice that values in top left corner are the same with the small input (except at boundary) | ||||
|         >>> m(input_3x3) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1.0000  1.2500  1.7500  1.5000  0.5000  0.0000 | ||||
|           1.5000  1.7500  2.2500  1.8750  0.6250  0.0000 | ||||
|           2.5000  2.7500  3.2500  2.6250  0.8750  0.0000 | ||||
|           2.2500  2.4375  2.8125  2.2500  0.7500  0.0000 | ||||
|           0.7500  0.8125  0.9375  0.7500  0.2500  0.0000 | ||||
|           0.0000  0.0000  0.0000  0.0000  0.0000  0.0000 | ||||
|         [torch.FloatTensor of size (1,1,6,6)] | ||||
|         tensor([[[[ 1.0000,  1.2500,  1.7500,  1.5000,  0.5000,  0.0000], | ||||
|                   [ 1.5000,  1.7500,  2.2500,  1.8750,  0.6250,  0.0000], | ||||
|                   [ 2.5000,  2.7500,  3.2500,  2.6250,  0.8750,  0.0000], | ||||
|                   [ 2.2500,  2.4375,  2.8125,  2.2500,  0.7500,  0.0000], | ||||
|                   [ 0.7500,  0.8125,  0.9375,  0.7500,  0.2500,  0.0000], | ||||
|                   [ 0.0000,  0.0000,  0.0000,  0.0000,  0.0000,  0.0000]]]]) | ||||
|  | ||||
|         >>> m = nn.Upsample(scale_factor=2, mode='bilinear', align_corners=True) | ||||
|         >>> # Notice that values in top left corner are now changed | ||||
|         >>> m(input_3x3) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1.0000  1.4000  1.8000  1.6000  0.8000  0.0000 | ||||
|           1.8000  2.2000  2.6000  2.2400  1.1200  0.0000 | ||||
|           2.6000  3.0000  3.4000  2.8800  1.4400  0.0000 | ||||
|           2.4000  2.7200  3.0400  2.5600  1.2800  0.0000 | ||||
|           1.2000  1.3600  1.5200  1.2800  0.6400  0.0000 | ||||
|           0.0000  0.0000  0.0000  0.0000  0.0000  0.0000 | ||||
|         [torch.FloatTensor of size (1,1,6,6)] | ||||
|  | ||||
|         tensor([[[[ 1.0000,  1.4000,  1.8000,  1.6000,  0.8000,  0.0000], | ||||
|                   [ 1.8000,  2.2000,  2.6000,  2.2400,  1.1200,  0.0000], | ||||
|                   [ 2.6000,  3.0000,  3.4000,  2.8800,  1.4400,  0.0000], | ||||
|                   [ 2.4000,  2.7200,  3.0400,  2.5600,  1.2800,  0.0000], | ||||
|                   [ 1.2000,  1.3600,  1.5200,  1.2800,  0.6400,  0.0000], | ||||
|                   [ 0.0000,  0.0000,  0.0000,  0.0000,  0.0000,  0.0000]]]]) | ||||
|     """ | ||||
|  | ||||
|     def __init__(self, size=None, scale_factor=None, mode='nearest', align_corners=None): | ||||
| @ -176,22 +156,15 @@ class UpsamplingNearest2d(Upsample): | ||||
|  | ||||
|         >>> input = torch.arange(1, 5).view(1, 1, 2, 2) | ||||
|         >>> input | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1  2 | ||||
|           3  4 | ||||
|         [torch.FloatTensor of size (1,1,2,2)] | ||||
|         tensor([[[[ 1.,  2.], | ||||
|                   [ 3.,  4.]]]]) | ||||
|  | ||||
|         >>> m = nn.UpsamplingNearest2d(scale_factor=2) | ||||
|         >>> m(input) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1  1  2  2 | ||||
|           1  1  2  2 | ||||
|           3  3  4  4 | ||||
|           3  3  4  4 | ||||
|         [torch.FloatTensor of size (1,1,4,4)] | ||||
|  | ||||
|         tensor([[[[ 1.,  1.,  2.,  2.], | ||||
|                   [ 1.,  1.,  2.,  2.], | ||||
|                   [ 3.,  3.,  4.,  4.], | ||||
|                   [ 3.,  3.,  4.,  4.]]]]) | ||||
|     """ | ||||
|     def __init__(self, size=None, scale_factor=None): | ||||
|         super(UpsamplingNearest2d, self).__init__(size, scale_factor, mode='nearest') | ||||
| @ -231,22 +204,15 @@ class UpsamplingBilinear2d(Upsample): | ||||
|  | ||||
|         >>> input = torch.arange(1, 5).view(1, 1, 2, 2) | ||||
|         >>> input | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1  2 | ||||
|           3  4 | ||||
|         [torch.FloatTensor of size (1,1,2,2)] | ||||
|         tensor([[[[ 1.,  2.], | ||||
|                   [ 3.,  4.]]]]) | ||||
|  | ||||
|         >>> m = nn.UpsamplingBilinear2d(scale_factor=2) | ||||
|         >>> m(input) | ||||
|  | ||||
|         (0 ,0 ,.,.) = | ||||
|           1.0000  1.3333  1.6667  2.0000 | ||||
|           1.6667  2.0000  2.3333  2.6667 | ||||
|           2.3333  2.6667  3.0000  3.3333 | ||||
|           3.0000  3.3333  3.6667  4.0000 | ||||
|         [torch.FloatTensor of size (1,1,4,4)] | ||||
|  | ||||
|         tensor([[[[ 1.0000,  1.3333,  1.6667,  2.0000], | ||||
|                   [ 1.6667,  2.0000,  2.3333,  2.6667], | ||||
|                   [ 2.3333,  2.6667,  3.0000,  3.3333], | ||||
|                   [ 3.0000,  3.3333,  3.6667,  4.0000]]]]) | ||||
|     """ | ||||
|     def __init__(self, size=None, scale_factor=None): | ||||
|         super(UpsamplingBilinear2d, self).__init__(size, scale_factor, mode='bilinear', align_corners=True) | ||||
|  | ||||
| @ -318,19 +318,11 @@ def pack_sequence(sequences): | ||||
|  | ||||
|     Example: | ||||
|         >>> from torch.nn.utils.rnn import pack_sequence | ||||
|         >>> a = torch.Tensor([1,2,3]) | ||||
|         >>> b = torch.Tensor([4,5]) | ||||
|         >>> c = torch.Tensor([6]) | ||||
|         >>> a = torch.tensor([1,2,3]) | ||||
|         >>> b = torch.tensor([4,5]) | ||||
|         >>> c = torch.tensor([6]) | ||||
|         >>> pack_sequence([a, b, c]]) | ||||
|         PackedSequence(data= | ||||
|          1 | ||||
|          4 | ||||
|          6 | ||||
|          2 | ||||
|          5 | ||||
|          3 | ||||
|         [torch.FloatTensor of size 6] | ||||
|         , batch_sizes=[3, 2, 1]) | ||||
|         PackedSequence(data=tensor([ 1,  4,  6,  2,  5,  3]), batch_sizes=tensor([ 3,  2,  1])) | ||||
|  | ||||
|  | ||||
|     Arguments: | ||||
|  | ||||
| @ -152,7 +152,7 @@ def save(obj, f, pickle_module=pickle, pickle_protocol=DEFAULT_PROTOCOL): | ||||
|  | ||||
|     Example: | ||||
|         >>> # Save to file | ||||
|         >>> x = torch.Tensor([0, 1, 2, 3, 4]) | ||||
|         >>> x = torch.tensor([0, 1, 2, 3, 4]) | ||||
|         >>> torch.save(x, 'tensor.pt') | ||||
|         >>> # Save to io.BytesIO buffer | ||||
|         >>> buffer = io.BytesIO() | ||||
|  | ||||
| @ -1,4 +1,5 @@ | ||||
| import torch | ||||
| import warnings | ||||
|  | ||||
|  | ||||
| def detach_variable(inputs): | ||||
| @ -14,10 +15,16 @@ def detach_variable(inputs): | ||||
|             "Only tuple of tensors is supported. Got Unsupported input type: ", type(inputs).__name__) | ||||
|  | ||||
|  | ||||
| def check_backward_validity(inputs): | ||||
|     if not any(inp.requires_grad for inp in inputs): | ||||
|         warnings.warn("None of the inputs have requires_grad=True. Gradients will be None") | ||||
|  | ||||
|  | ||||
| class CheckpointFunction(torch.autograd.Function): | ||||
|  | ||||
|     @staticmethod | ||||
|     def forward(ctx, run_function, *args): | ||||
|         check_backward_validity(args) | ||||
|         ctx.run_function = run_function | ||||
|         ctx.save_for_backward(*args) | ||||
|         with torch.no_grad(): | ||||
| @ -66,6 +73,11 @@ def checkpoint(function, *args): | ||||
|         checkpointed version won't be equivalent, and unfortunately it can't be | ||||
|         detected. | ||||
|  | ||||
|     .. warning: | ||||
|         At least one of the inputs needs to have :code:`requires_grad=True` if | ||||
|         grads are needed for model inputs, otherwise the checkpointed part of the | ||||
|         model won't have gradients. | ||||
|  | ||||
|     Args: | ||||
|         function: describes what to run in the forward pass of the model or | ||||
|             part of the model. It should also know how to handle the inputs | ||||
| @ -96,6 +108,11 @@ def checkpoint_sequential(functions, segments, *inputs): | ||||
|         Checkpointing doesn't work with :func:`torch.autograd.grad`, but only | ||||
|         with :func:`torch.autograd.backward`. | ||||
|  | ||||
|     .. warning: | ||||
|         At least one of the inputs needs to have :code:`requires_grad=True` if | ||||
|         grads are needed for model inputs, otherwise the checkpointed part of the | ||||
|         model won't have gradients. | ||||
|  | ||||
|     Args: | ||||
|         functions: A :class:`torch.nn.Sequential` or the list of modules or | ||||
|             functions (comprising the model) to run sequentially. | ||||
|  | ||||
		Reference in New Issue
	
	Block a user
	