Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
BaiXuePrincess
Paddle
提交
a99fd15e
P
Paddle
项目概览
BaiXuePrincess
/
Paddle
与 Fork 源项目一致
Fork自
PaddlePaddle / Paddle
通知
1
Star
1
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
P
Paddle
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
“dcfe198631058dbcd4fe6e887a4e514008ed1e68”上不存在“paddle/phi/kernels/reduce_sum_grad_kernel.h”
提交
a99fd15e
编写于
12月 14, 2021
作者:
J
jim19930609
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Moved LoDTensor methods/members to Tensor
上级
19a833c8
变更
5
隐藏空白更改
内联
并排
Showing
5 changed file
with
259 addition
and
254 deletion
+259
-254
paddle/fluid/framework/lod_tensor.cc
paddle/fluid/framework/lod_tensor.cc
+3
-178
paddle/fluid/framework/lod_tensor.h
paddle/fluid/framework/lod_tensor.h
+9
-73
paddle/fluid/framework/mixed_vector.h
paddle/fluid/framework/mixed_vector.h
+1
-2
paddle/fluid/framework/tensor.cc
paddle/fluid/framework/tensor.cc
+177
-0
paddle/fluid/framework/tensor.h
paddle/fluid/framework/tensor.h
+69
-1
未找到文件。
paddle/fluid/framework/lod_tensor.cc
浏览文件 @
a99fd15e
...
...
@@ -151,7 +151,8 @@ bool CheckLoD(const LoD &in, int tensor_height) {
}
// check: the lowest level's last offset should equals `tensor_height` if
// tensor_height>0.
if
(
tensor_height
>
0
&&
(
size_t
)
tensor_height
!=
in
.
back
().
back
())
if
(
tensor_height
>
0
&&
static_cast
<
size_t
>
(
tensor_height
)
!=
in
.
back
().
back
())
return
false
;
// check: the higher level's last offset should equals the lower level's
...
...
@@ -184,42 +185,13 @@ bool CheckAbsLoD(const LoD &in, int tensor_height) {
if
(
level
.
front
()
!=
0
)
return
false
;
if
(
tensor_height
<
0
)
{
tensor_height
=
level
.
back
();
}
else
if
(
(
size_t
)
tensor_height
!=
level
.
back
())
{
}
else
if
(
static_cast
<
size_t
>
(
tensor_height
)
!=
level
.
back
())
{
return
false
;
}
}
return
true
;
}
using
LoDAndOffset
=
std
::
pair
<
LoD
,
std
::
pair
<
size_t
,
size_t
>>
;
LoDAndOffset
GetSubLoDAndAbsoluteOffset
(
const
LoD
&
lod
,
size_t
start_idx
,
size_t
end_idx
,
size_t
start_level
)
{
LoD
sub_lod
;
for
(
size_t
level_idx
=
start_level
;
level_idx
<
lod
.
size
();
++
level_idx
)
{
PADDLE_ENFORCE_LE
(
start_idx
,
end_idx
,
platform
::
errors
::
InvalidArgument
(
"The start index should be less than the end index, "
"but received start index is %d, end index is %d."
,
start_idx
,
end_idx
));
PADDLE_ENFORCE_LT
(
end_idx
,
lod
[
level_idx
].
size
(),
platform
::
errors
::
InvalidArgument
(
"The end index should be less than the LoD level size, but "
"received end index is %d, LoD level size is %d."
,
end_idx
,
lod
[
level_idx
].
size
()));
std
::
vector
<
size_t
>
level_lens
;
for
(
size_t
i
=
start_idx
;
i
<
end_idx
;
++
i
)
{
level_lens
.
push_back
(
lod
[
level_idx
][
i
+
1
]
-
lod
[
level_idx
][
i
]);
}
sub_lod
.
emplace_back
(
level_lens
);
start_idx
=
lod
[
level_idx
][
start_idx
];
end_idx
=
lod
[
level_idx
][
end_idx
];
}
return
LoDAndOffset
{
sub_lod
,
{
start_idx
,
end_idx
}};
}
void
AppendLoD
(
LoD
*
lod
,
const
LoD
&
lod_length
)
{
PADDLE_ENFORCE
(
lod
->
empty
()
||
lod
->
size
()
==
lod_length
.
size
(),
...
...
@@ -347,153 +319,6 @@ void DeserializeFromStream(std::istream &is, LoDTensor *tensor,
TensorFromStream
(
is
,
static_cast
<
Tensor
*>
(
tensor
),
dev_ctx
);
}
std
::
vector
<
LoDTensor
>
LoDTensor
::
SplitLoDTensor
(
const
std
::
vector
<
platform
::
Place
>
places
)
const
{
PADDLE_ENFORCE_GT
(
places
.
size
(),
0
,
platform
::
errors
::
InvalidArgument
(
"Place number cannot be empty when splitting."
));
check_memory_size
();
size_t
batch_size
=
lod
().
empty
()
?
static_cast
<
size_t
>
(
dims
()[
0
])
:
lod
()[
0
].
size
()
-
1
;
// if batch_size is 0, just return #places.size() copys of empty
// tensors.
if
(
batch_size
==
0
)
{
std
::
vector
<
LoDTensor
>
empty_results
;
empty_results
.
reserve
(
places
.
size
());
for
(
size_t
i
=
0
;
i
<
places
.
size
();
++
i
)
{
LoDTensor
dst
;
dst
.
Resize
(
dims
());
dst
.
mutable_data
(
places
[
i
],
type
());
if
(
!
lod
().
empty
())
{
dst
.
set_lod
(
lod
());
}
empty_results
.
emplace_back
(
std
::
move
(
dst
));
}
return
empty_results
;
}
auto
step_width
=
(
batch_size
+
places
.
size
()
-
1
)
/
places
.
size
();
auto
result_size
=
(
batch_size
+
step_width
-
1
)
/
step_width
;
std
::
vector
<
LoDTensor
>
results
;
results
.
reserve
(
result_size
);
for
(
size_t
i
=
0
;
i
<
result_size
;
++
i
)
{
auto
begin
=
i
*
step_width
;
auto
end
=
std
::
min
<
size_t
>
((
i
+
1
)
*
step_width
,
batch_size
);
PADDLE_ENFORCE_LT
(
begin
,
end
,
platform
::
errors
::
InvalidArgument
(
"The begin index must be less than the end index, "
"but received begin index is %d, end index is %d."
,
begin
,
end
));
LoDTensor
dst
;
if
(
lod
().
empty
())
{
auto
src
=
Slice
(
begin
,
end
);
auto
&
dst_place
=
places
[
i
];
framework
::
TensorCopy
(
src
,
dst_place
,
&
dst
);
}
else
{
auto
lod_and_offset
=
GetSubLoDAndAbsoluteOffset
(
lod
(),
begin
,
end
,
0
);
auto
&
offset
=
lod_and_offset
.
second
;
auto
src
=
Slice
(
offset
.
first
,
offset
.
second
);
auto
&
dst_place
=
places
[
i
];
framework
::
TensorCopy
(
src
,
dst_place
,
&
dst
);
LoD
my_lod
;
for
(
auto
&
l
:
lod_and_offset
.
first
)
{
std
::
vector
<
size_t
>
v
{
0
};
for
(
auto
&
ll
:
l
)
{
v
.
push_back
(
ll
+
v
.
back
());
}
my_lod
.
emplace_back
(
v
);
}
dst
.
set_lod
(
my_lod
);
}
results
.
emplace_back
(
std
::
move
(
dst
));
}
return
results
;
}
void
LoDTensor
::
MergeLoDTensor
(
const
std
::
vector
<
const
LoDTensor
*>
&
lod_tensors
,
platform
::
Place
dst_place
)
{
PADDLE_ENFORCE_EQ
(
lod_tensors
.
empty
(),
false
,
platform
::
errors
::
InvalidArgument
(
"The LoDTensors to be merged are empty."
));
framework
::
DDim
new_dim
=
lod_tensors
[
0
]
->
dims
();
proto
::
VarType
::
Type
new_type
=
proto
::
VarType
::
FP32
;
framework
::
DataLayout
new_layout
=
lod_tensors
[
0
]
->
layout
();
for
(
auto
*
t
:
lod_tensors
)
{
if
(
t
->
numel
()
&&
t
->
IsInitialized
())
{
new_dim
=
t
->
dims
();
new_type
=
t
->
type
();
new_layout
=
t
->
layout
();
break
;
}
}
LoD
new_lod
=
lod_tensors
[
0
]
->
lod
();
for
(
size_t
i
=
1
;
i
<
lod_tensors
.
size
();
++
i
)
{
auto
*
t
=
lod_tensors
[
i
];
if
(
t
->
numel
()
&&
t
->
IsInitialized
())
{
PADDLE_ENFORCE_EQ
(
new_type
,
t
->
type
(),
platform
::
errors
::
InvalidArgument
(
"LoDTensor data type does not match, expected type is %s, actual "
"type is %s."
,
DataTypeToString
(
new_type
),
DataTypeToString
(
t
->
type
())));
PADDLE_ENFORCE_EQ
(
new_layout
,
t
->
layout
(),
platform
::
errors
::
InvalidArgument
(
"LoDTensor layout does not match, expected layout is %s, "
"actual layout is %s."
,
DataLayoutToString
(
new_layout
),
DataLayoutToString
(
t
->
layout
())));
PADDLE_ENFORCE_EQ
(
framework
::
product
(
new_dim
)
/
new_dim
[
0
],
framework
::
product
(
t
->
dims
())
/
t
->
dims
()[
0
],
platform
::
errors
::
InvalidArgument
(
"LoDTensor dimension does not match, all dimensions except the "
"first dimension need to be equal,"
"but expected dimension is %s, actual dimension is %s."
,
new_dim
,
t
->
dims
()));
new_dim
[
0
]
+=
t
->
dims
()[
0
];
}
auto
&
lod
=
t
->
lod
();
PADDLE_ENFORCE_EQ
(
new_lod
.
size
(),
lod
.
size
(),
platform
::
errors
::
InvalidArgument
(
"The LoD information of LoDTensor does not match, "
"expected LoD is %s, actual LoD is %s."
,
new_lod
,
lod
));
for
(
size_t
j
=
0
;
j
<
lod
.
size
();
++
j
)
{
auto
&
sub_lod
=
new_lod
[
j
];
size_t
offset
=
sub_lod
.
back
();
for
(
size_t
k
=
1
;
k
<
lod
[
j
].
size
();
++
k
)
{
sub_lod
.
push_back
(
lod
[
j
][
k
]
+
offset
);
}
}
}
Resize
(
new_dim
);
set_layout
(
new_layout
);
set_lod
(
new_lod
);
mutable_data
(
dst_place
,
new_type
);
int
begin
=
0
;
for
(
auto
*
src
:
lod_tensors
)
{
int
end
=
begin
+
src
->
dims
()[
0
];
if
(
end
==
begin
)
{
continue
;
}
auto
dst
=
Slice
(
begin
,
end
);
framework
::
TensorCopy
(
*
src
,
dst_place
,
&
dst
);
begin
=
end
;
}
}
LoD
ConvertToLengthBasedLoD
(
const
LoD
&
offset_lod
)
{
LoD
length_lod
;
length_lod
.
reserve
(
offset_lod
.
size
());
...
...
paddle/fluid/framework/lod_tensor.h
浏览文件 @
a99fd15e
...
...
@@ -39,6 +39,8 @@ class DeviceContext;
namespace
paddle
{
namespace
framework
{
using
LoD
=
std
::
vector
<
Vector
<
size_t
>>
;
/*
* LoD is short for Level of Details.
*
...
...
@@ -54,7 +56,6 @@ namespace framework {
* 0 2 4 7
* 0 2 5 7 10 12 15 20
*/
using
LoD
=
std
::
vector
<
Vector
<
size_t
>>
;
std
::
ostream
&
operator
<<
(
std
::
ostream
&
os
,
const
LoD
&
lod
);
std
::
ostream
&
operator
<<
(
std
::
ostream
&
os
,
const
LoDTensor
&
t
);
...
...
@@ -108,64 +109,14 @@ bool CheckAbsLoD(const LoD& in, int tensor_height = -1);
*/
class
LoDTensor
:
public
Tensor
{
public:
LoDTensor
()
:
Tensor
()
{}
explicit
LoDTensor
(
const
LoD
&
lod
)
:
lod_
(
lod
)
{}
void
set_lod
(
const
LoD
&
lod
)
{
lod_
=
lod
;
}
const
LoD
&
lod
()
const
{
return
lod_
;
}
LoD
*
mutable_lod
()
{
return
&
lod_
;
}
/*
* Get the start offset and end offset of an element from LoD.
*/
std
::
pair
<
size_t
,
size_t
>
lod_element
(
size_t
level
,
size_t
elem
)
const
{
PADDLE_ENFORCE_LT
(
level
,
NumLevels
(),
platform
::
errors
::
InvalidArgument
(
"The input level of LoD is invalid, it should be less than LoD "
"size. The input level is %zu, the LoD size is %zu."
,
level
,
NumLevels
()));
PADDLE_ENFORCE_LT
(
elem
,
NumElements
(
level
),
platform
::
errors
::
InvalidArgument
(
"The input element of LoD is invalid, it should be "
"less than the number of elements in its level."
"The input element is %zu, the number of elements in "
"its level is %zu."
,
elem
,
NumElements
(
level
)));
return
std
::
make_pair
((
lod_
)[
level
][
elem
],
(
lod_
)[
level
][
elem
+
1
]);
}
/*
* Number of LoDTensor's levels, each level has units of data, for example,
* in the sentence's view, article, paragraph, sentence are 3 levels.
*/
size_t
NumLevels
()
const
{
return
lod_
.
size
();
}
/*
* Number of elements in a level.
*/
size_t
NumElements
(
size_t
level
=
0
)
const
{
PADDLE_ENFORCE_LT
(
level
,
NumLevels
(),
platform
::
errors
::
InvalidArgument
(
"The input level of LoD is invalid, it should be less than LoD "
"size. The input level is %zu, the LoD size is %zu."
,
level
,
NumLevels
()));
// the last offset is the end of last element
return
(
lod_
)[
level
].
size
()
-
1
;
}
// Split LoDTensor and copy to each place specified in places.
std
::
vector
<
LoDTensor
>
SplitLoDTensor
(
const
std
::
vector
<
platform
::
Place
>
places
)
const
;
void
MergeLoDTensor
(
const
std
::
vector
<
const
LoDTensor
*>&
lod_tensors
,
platform
::
Place
place
);
private:
LoD
lod_
;
platform
::
Place
place
)
{
std
::
vector
<
const
Tensor
*>
tmp
;
for
(
const
LoDTensor
*
lod_tensor
:
lod_tensors
)
{
tmp
.
push_back
(
lod_tensor
);
}
Tensor
::
MergeLoDTensor
(
tmp
,
place
);
}
};
/*
...
...
@@ -210,21 +161,6 @@ LoDTensor LodExpand(const LoDTensor& source, const LoD& lod, size_t level,
return
tensor
;
}
// Get the absolute offset of a lod[start_level][start_idx:end_idx] and
// relative length of details for every levels(i.e., [start_level: ]).
//
// For example,
// lod = [[0, 3, 4, 8], [0, 9, 10, 11, 13, 17, 19, 22, 24]]
// start_level = 0
// start_idx = 1
// end_idx = 3
//
// Returns:
// LoD = [[1, 4], [2, 4, 2, 3, 2]]
// pair<size_t, size_t> = {11, 24}
std
::
pair
<
LoD
,
std
::
pair
<
size_t
,
size_t
>>
GetSubLoDAndAbsoluteOffset
(
const
LoD
&
lod
,
size_t
start_idx
,
size_t
end_idx
,
size_t
start_level
);
void
AppendLoD
(
LoD
*
lod
,
const
LoD
&
lod_length
);
/*
...
...
paddle/fluid/framework/mixed_vector.h
浏览文件 @
a99fd15e
...
...
@@ -23,10 +23,9 @@ limitations under the License. */
#include "glog/logging.h"
#include "paddle/fluid/framework/details/cow_ptr.h"
#include "paddle/fluid/framework/tensor.h"
#include "paddle/fluid/framework/tensor_util.h"
#include "paddle/fluid/memory/malloc.h"
#include "paddle/fluid/memory/memcpy.h"
#include "paddle/fluid/platform/device_context.h"
#include "paddle/utils/none.h"
#include "paddle/utils/optional.h"
...
...
paddle/fluid/framework/tensor.cc
浏览文件 @
a99fd15e
...
...
@@ -13,6 +13,7 @@ See the License for the specific language governing permissions and
limitations under the License. */
#include "paddle/fluid/framework/tensor.h"
#include "paddle/fluid/framework/tensor_util.h"
DECLARE_bool
(
use_stream_safe_cuda_allocator
);
...
...
@@ -235,5 +236,181 @@ void Tensor::ResetHolderWithType(std::shared_ptr<memory::Allocation> holder,
void
Tensor
::
set_type
(
const
proto
::
VarType
::
Type
&
type
)
{
type_
=
type
;
}
/* ---------------------------------------- */
/* -------------- LoDTensor --------------- */
/* ---------------------------------------- */
using
LoDAndOffset
=
std
::
pair
<
LoD
,
std
::
pair
<
size_t
,
size_t
>>
;
LoDAndOffset
GetSubLoDAndAbsoluteOffset
(
const
LoD
&
lod
,
size_t
start_idx
,
size_t
end_idx
,
size_t
start_level
)
{
LoD
sub_lod
;
for
(
size_t
level_idx
=
start_level
;
level_idx
<
lod
.
size
();
++
level_idx
)
{
PADDLE_ENFORCE_LE
(
start_idx
,
end_idx
,
platform
::
errors
::
InvalidArgument
(
"The start index should be less than the end index, "
"but received start index is %d, end index is %d."
,
start_idx
,
end_idx
));
PADDLE_ENFORCE_LT
(
end_idx
,
lod
[
level_idx
].
size
(),
platform
::
errors
::
InvalidArgument
(
"The end index should be less than the LoD level size, but "
"received end index is %d, LoD level size is %d."
,
end_idx
,
lod
[
level_idx
].
size
()));
std
::
vector
<
size_t
>
level_lens
;
for
(
size_t
i
=
start_idx
;
i
<
end_idx
;
++
i
)
{
level_lens
.
push_back
(
lod
[
level_idx
][
i
+
1
]
-
lod
[
level_idx
][
i
]);
}
sub_lod
.
emplace_back
(
level_lens
);
start_idx
=
lod
[
level_idx
][
start_idx
];
end_idx
=
lod
[
level_idx
][
end_idx
];
}
return
LoDAndOffset
{
sub_lod
,
{
start_idx
,
end_idx
}};
}
std
::
vector
<
Tensor
>
Tensor
::
SplitLoDTensor
(
const
std
::
vector
<
platform
::
Place
>
places
)
const
{
PADDLE_ENFORCE_GT
(
places
.
size
(),
0
,
platform
::
errors
::
InvalidArgument
(
"Place number cannot be empty when splitting."
));
check_memory_size
();
size_t
batch_size
=
lod
().
empty
()
?
static_cast
<
size_t
>
(
dims
()[
0
])
:
lod
()[
0
].
size
()
-
1
;
// if batch_size is 0, just return #places.size() copys of empty
// tensors.
if
(
batch_size
==
0
)
{
std
::
vector
<
Tensor
>
empty_results
;
empty_results
.
reserve
(
places
.
size
());
for
(
size_t
i
=
0
;
i
<
places
.
size
();
++
i
)
{
Tensor
dst
;
dst
.
Resize
(
dims
());
dst
.
mutable_data
(
places
[
i
],
type
());
if
(
!
lod
().
empty
())
{
dst
.
set_lod
(
lod
());
}
empty_results
.
emplace_back
(
std
::
move
(
dst
));
}
return
empty_results
;
}
auto
step_width
=
(
batch_size
+
places
.
size
()
-
1
)
/
places
.
size
();
auto
result_size
=
(
batch_size
+
step_width
-
1
)
/
step_width
;
std
::
vector
<
Tensor
>
results
;
results
.
reserve
(
result_size
);
for
(
size_t
i
=
0
;
i
<
result_size
;
++
i
)
{
auto
begin
=
i
*
step_width
;
auto
end
=
std
::
min
<
size_t
>
((
i
+
1
)
*
step_width
,
batch_size
);
PADDLE_ENFORCE_LT
(
begin
,
end
,
platform
::
errors
::
InvalidArgument
(
"The begin index must be less than the end index, "
"but received begin index is %d, end index is %d."
,
begin
,
end
));
Tensor
dst
;
if
(
lod
().
empty
())
{
auto
src
=
Slice
(
begin
,
end
);
auto
&
dst_place
=
places
[
i
];
framework
::
TensorCopy
(
src
,
dst_place
,
&
dst
);
}
else
{
auto
lod_and_offset
=
GetSubLoDAndAbsoluteOffset
(
lod
(),
begin
,
end
,
0
);
auto
&
offset
=
lod_and_offset
.
second
;
auto
src
=
Slice
(
offset
.
first
,
offset
.
second
);
auto
&
dst_place
=
places
[
i
];
framework
::
TensorCopy
(
src
,
dst_place
,
&
dst
);
LoD
my_lod
;
for
(
auto
&
l
:
lod_and_offset
.
first
)
{
std
::
vector
<
size_t
>
v
{
0
};
for
(
auto
&
ll
:
l
)
{
v
.
push_back
(
ll
+
v
.
back
());
}
my_lod
.
emplace_back
(
v
);
}
dst
.
set_lod
(
my_lod
);
}
results
.
emplace_back
(
std
::
move
(
dst
));
}
return
results
;
}
void
Tensor
::
MergeLoDTensor
(
const
std
::
vector
<
const
Tensor
*>&
lod_tensors
,
platform
::
Place
dst_place
)
{
PADDLE_ENFORCE_EQ
(
lod_tensors
.
empty
(),
false
,
platform
::
errors
::
InvalidArgument
(
"The LoDTensors to be merged are empty."
));
framework
::
DDim
new_dim
=
lod_tensors
[
0
]
->
dims
();
proto
::
VarType
::
Type
new_type
=
proto
::
VarType
::
FP32
;
framework
::
DataLayout
new_layout
=
lod_tensors
[
0
]
->
layout
();
for
(
auto
*
t
:
lod_tensors
)
{
if
(
t
->
numel
()
&&
t
->
IsInitialized
())
{
new_dim
=
t
->
dims
();
new_type
=
t
->
type
();
new_layout
=
t
->
layout
();
break
;
}
}
LoD
new_lod
=
lod_tensors
[
0
]
->
lod
();
for
(
size_t
i
=
1
;
i
<
lod_tensors
.
size
();
++
i
)
{
auto
*
t
=
lod_tensors
[
i
];
if
(
t
->
numel
()
&&
t
->
IsInitialized
())
{
PADDLE_ENFORCE_EQ
(
new_type
,
t
->
type
(),
platform
::
errors
::
InvalidArgument
(
"LoDTensor data type does not match, expected type is %s, actual "
"type is %s."
,
DataTypeToString
(
new_type
),
DataTypeToString
(
t
->
type
())));
PADDLE_ENFORCE_EQ
(
new_layout
,
t
->
layout
(),
platform
::
errors
::
InvalidArgument
(
"LoDTensor layout does not match, expected layout is %s, "
"actual layout is %s."
,
DataLayoutToString
(
new_layout
),
DataLayoutToString
(
t
->
layout
())));
PADDLE_ENFORCE_EQ
(
framework
::
product
(
new_dim
)
/
new_dim
[
0
],
framework
::
product
(
t
->
dims
())
/
t
->
dims
()[
0
],
platform
::
errors
::
InvalidArgument
(
"LoDTensor dimension does not match, all dimensions except the "
"first dimension need to be equal,"
"but expected dimension is %s, actual dimension is %s."
,
new_dim
,
t
->
dims
()));
new_dim
[
0
]
+=
t
->
dims
()[
0
];
}
auto
&
lod
=
t
->
lod
();
PADDLE_ENFORCE_EQ
(
new_lod
.
size
(),
lod
.
size
(),
platform
::
errors
::
InvalidArgument
(
"The LoD information of LoDTensor does not match"
));
for
(
size_t
j
=
0
;
j
<
lod
.
size
();
++
j
)
{
auto
&
sub_lod
=
new_lod
[
j
];
size_t
offset
=
sub_lod
.
back
();
for
(
size_t
k
=
1
;
k
<
lod
[
j
].
size
();
++
k
)
{
sub_lod
.
push_back
(
lod
[
j
][
k
]
+
offset
);
}
}
}
Resize
(
new_dim
);
set_layout
(
new_layout
);
set_lod
(
new_lod
);
mutable_data
(
dst_place
,
new_type
);
int
begin
=
0
;
for
(
auto
*
src
:
lod_tensors
)
{
int
end
=
begin
+
src
->
dims
()[
0
];
if
(
end
==
begin
)
{
continue
;
}
auto
dst
=
Slice
(
begin
,
end
);
framework
::
TensorCopy
(
*
src
,
dst_place
,
&
dst
);
begin
=
end
;
}
}
}
// namespace framework
}
// namespace paddle
paddle/fluid/framework/tensor.h
浏览文件 @
a99fd15e
...
...
@@ -24,6 +24,7 @@ limitations under the License. */
#include "paddle/fluid/framework/data_layout.h"
#include "paddle/fluid/framework/ddim.h"
#include "paddle/fluid/framework/framework.pb.h"
#include "paddle/fluid/framework/mixed_vector.h"
#include "paddle/fluid/memory/memory.h"
#include "paddle/fluid/platform/device_context.h"
#include "paddle/fluid/platform/enforce.h"
...
...
@@ -41,7 +42,7 @@ namespace paddle {
namespace
framework
{
class
LoDTensor
;
using
LoD
=
std
::
vector
<
Vector
<
size_t
>>
;
/*
NOTE(liym27): [ What is TensorInplaceVersion used for? ]
...
...
@@ -326,8 +327,75 @@ class Tensor {
*/
size_t
offset_
;
std
::
shared_ptr
<
TensorInplaceVersion
>
inplace_version_counter_
;
/* ---------------------------------------------------------- */
/* --------------- Reserved for LoDTensor ------------------- */
/* ---------------------------------------------------------- */
public:
explicit
Tensor
(
const
LoD
&
lod
)
:
lod_
(
lod
)
{}
void
set_lod
(
const
LoD
&
lod
)
{
lod_
=
lod
;
}
const
LoD
&
lod
()
const
{
return
lod_
;
}
LoD
*
mutable_lod
()
{
return
&
lod_
;
}
std
::
pair
<
size_t
,
size_t
>
lod_element
(
size_t
level
,
size_t
elem
)
const
{
PADDLE_ENFORCE_LT
(
level
,
NumLevels
(),
platform
::
errors
::
InvalidArgument
(
"The input level of LoD is invalid, it should be less than LoD "
"size. The input level is %zu, the LoD size is %zu."
,
level
,
NumLevels
()));
PADDLE_ENFORCE_LT
(
elem
,
NumElements
(
level
),
platform
::
errors
::
InvalidArgument
(
"The input element of LoD is invalid, it should be "
"less than the number of elements in its level."
"The input element is %zu, the number of elements in "
"its level is %zu."
,
elem
,
NumElements
(
level
)));
return
std
::
make_pair
((
lod_
)[
level
][
elem
],
(
lod_
)[
level
][
elem
+
1
]);
}
size_t
NumLevels
()
const
{
return
lod_
.
size
();
}
size_t
NumElements
(
size_t
level
=
0
)
const
{
PADDLE_ENFORCE_LT
(
level
,
NumLevels
(),
platform
::
errors
::
InvalidArgument
(
"The input level of LoD is invalid, it should be less than LoD "
"size. The input level is %zu, the LoD size is %zu."
,
level
,
NumLevels
()));
// the last offset is the end of last element
return
(
lod_
)[
level
].
size
()
-
1
;
}
// Split LoDTensor and copy to each place specified in places.
std
::
vector
<
Tensor
>
SplitLoDTensor
(
const
std
::
vector
<
platform
::
Place
>
places
)
const
;
void
MergeLoDTensor
(
const
std
::
vector
<
const
Tensor
*>&
lod_tensors
,
platform
::
Place
place
);
private:
LoD
lod_
;
};
// Get the absolute offset of a lod[start_level][start_idx:end_idx] and
// relative length of details for every levels(i.e., [start_level: ]).
//
// For example,
// lod = [[0, 3, 4, 8], [0, 9, 10, 11, 13, 17, 19, 22, 24]]
// start_level = 0
// start_idx = 1
// end_idx = 3
//
// Returns:
// LoD = [[1, 4], [2, 4, 2, 3, 2]]
// pair<size_t, size_t> = {11, 24}
std
::
pair
<
LoD
,
std
::
pair
<
size_t
,
size_t
>>
GetSubLoDAndAbsoluteOffset
(
const
LoD
&
lod
,
size_t
start_idx
,
size_t
end_idx
,
size_t
start_level
);
}
// namespace framework
}
// namespace paddle
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录