mirror of
https://github.com/boostorg/multi_index.git
synced 2026-07-21 13:23:43 +00:00
Compare commits
47 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 27dd132780 | |||
| f3ed1db062 | |||
| 6ee20e771a | |||
| b97bf1b88c | |||
| ff04062460 | |||
| 3352524030 | |||
| 06d92b4c12 | |||
| d95a94942b | |||
| 46e8b85d9f | |||
| 4018129915 | |||
| bb8603a8e8 | |||
| ef4399e4bc | |||
| 262f2e14d2 | |||
| 20cef54465 | |||
| 0b463d29f2 | |||
| e1299f8343 | |||
| 0a0e7284c7 | |||
| 5bbb047a30 | |||
| fef3e3e457 | |||
| 9ad2576e00 | |||
| da77e719f3 | |||
| c57cfda1c3 | |||
| d6d074a1e9 | |||
| 265bac6938 | |||
| 0a8bc28be8 | |||
| e0594b8ed7 | |||
| ef2767d7d1 | |||
| 82d74dabdc | |||
| a07500133d | |||
| fa7bb68b03 | |||
| 58342f7a79 | |||
| ae77699e7e | |||
| 26d5ffc7fb | |||
| e6e2d52fe3 | |||
| 2cf8cbe771 | |||
| 5bc2cb1905 | |||
| 4d858c2e41 | |||
| e939bfcf63 | |||
| f0f5c5bfaf | |||
| e27ca50b51 | |||
| e144a99544 | |||
| f45dd2a84b | |||
| 0be9e26b24 | |||
| 1ff9721761 | |||
| 7d25746bd1 | |||
| eebd34cb95 | |||
| d127461abe |
-486
@@ -1,486 +0,0 @@
|
||||
# Copyright 2022 Peter Dimov
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# https://www.boost.org/LICENSE_1_0.txt
|
||||
|
||||
local library = "multi_index";
|
||||
|
||||
local triggers =
|
||||
{
|
||||
branch: [ "master", "develop", "feature/*", "fix/*" ]
|
||||
};
|
||||
|
||||
local ubsan = { UBSAN: '1', UBSAN_OPTIONS: 'print_stacktrace=1' };
|
||||
local asan = { ASAN: '1' };
|
||||
|
||||
local linux_pipeline(name, image, environment, packages = "", sources = [], arch = "amd64") =
|
||||
{
|
||||
name: name,
|
||||
kind: "pipeline",
|
||||
type: "docker",
|
||||
trigger: triggers,
|
||||
platform:
|
||||
{
|
||||
os: "linux",
|
||||
arch: arch
|
||||
},
|
||||
steps:
|
||||
[
|
||||
{
|
||||
name: "everything",
|
||||
image: image,
|
||||
environment: environment,
|
||||
commands:
|
||||
[
|
||||
'set -e',
|
||||
'wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | apt-key add -',
|
||||
] +
|
||||
(if sources != [] then [ ('apt-add-repository "' + source + '"') for source in sources ] else []) +
|
||||
(if packages != "" then [ 'apt-get update', 'apt-get -y install ' + packages ] else []) +
|
||||
[
|
||||
'export LIBRARY=' + library,
|
||||
'./.drone/drone.sh',
|
||||
]
|
||||
}
|
||||
]
|
||||
};
|
||||
|
||||
local macos_pipeline(name, environment, xcode_version = "12.2", osx_version = "catalina", arch = "amd64") =
|
||||
{
|
||||
name: name,
|
||||
kind: "pipeline",
|
||||
type: "exec",
|
||||
trigger: triggers,
|
||||
platform: {
|
||||
"os": "darwin",
|
||||
"arch": arch
|
||||
},
|
||||
node: {
|
||||
"os": osx_version
|
||||
},
|
||||
steps: [
|
||||
{
|
||||
name: "everything",
|
||||
environment: environment + { "DEVELOPER_DIR": "/Applications/Xcode-" + xcode_version + ".app/Contents/Developer" },
|
||||
commands:
|
||||
[
|
||||
'export LIBRARY=' + library,
|
||||
'./.drone/drone.sh',
|
||||
]
|
||||
}
|
||||
]
|
||||
};
|
||||
|
||||
local windows_pipeline(name, image, environment, arch = "amd64") =
|
||||
{
|
||||
name: name,
|
||||
kind: "pipeline",
|
||||
type: "docker",
|
||||
trigger: triggers,
|
||||
platform:
|
||||
{
|
||||
os: "windows",
|
||||
arch: arch
|
||||
},
|
||||
"steps":
|
||||
[
|
||||
{
|
||||
name: "everything",
|
||||
image: image,
|
||||
environment: environment,
|
||||
commands:
|
||||
[
|
||||
'cmd /C .drone\\\\drone.bat ' + library,
|
||||
]
|
||||
}
|
||||
]
|
||||
};
|
||||
|
||||
[
|
||||
linux_pipeline(
|
||||
"Linux 14.04 GCC 4.8* 32/64",
|
||||
"cppalliance/droneubuntu1404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++', CXXSTD: '11', ADDRMD: '32,64' },
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 14.04 GCC 4.9 32/64",
|
||||
"cppalliance/droneubuntu1404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-4.9', CXXSTD: '11', ADDRMD: '32,64' },
|
||||
"g++-4.9-multilib",
|
||||
[ "ppa:ubuntu-toolchain-r/test" ],
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 16.04 GCC 5* 32/64",
|
||||
"cppalliance/droneubuntu1604:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++', CXXSTD: '11,14', ADDRMD: '32,64' },
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 18.04 GCC 6 32/64",
|
||||
"cppalliance/droneubuntu1804:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-6', CXXSTD: '11,14', ADDRMD: '32,64' },
|
||||
"g++-6-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 18.04 GCC 7* 32/64",
|
||||
"cppalliance/droneubuntu1804:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++', CXXSTD: '11,14,17', ADDRMD: '32,64' },
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 18.04 GCC 8 32/64",
|
||||
"cppalliance/droneubuntu1804:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-8', CXXSTD: '11,14,17', ADDRMD: '32,64' },
|
||||
"g++-8-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 GCC 9* 32/64",
|
||||
"cppalliance/droneubuntu2004:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++', CXXSTD: '11,14,17,2a', ADDRMD: '32,64' },
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 GCC 9* ARM64",
|
||||
"cppalliance/droneubuntu2004:multiarch",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++', CXXSTD: '11,14,17,2a' },
|
||||
arch="arm64",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 GCC 9* S390x",
|
||||
"cppalliance/droneubuntu2004:multiarch",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++', CXXSTD: '11,14,17,2a' },
|
||||
arch="s390x",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 GCC 10 32/64",
|
||||
"cppalliance/droneubuntu2004:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-10', CXXSTD: '11,14,17,20', ADDRMD: '32,64' },
|
||||
"g++-10-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 22.04 GCC 11* 32/64",
|
||||
"cppalliance/droneubuntu2204:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++', CXXSTD: '11,14,17,2a', ADDRMD: '32,64' },
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 22.04 GCC 12 32/64 C++11-14",
|
||||
"cppalliance/droneubuntu2204:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-12', CXXSTD: '11,14', ADDRMD: '32,64' },
|
||||
"g++-12-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 22.04 GCC 12 32/64 C++17-20",
|
||||
"cppalliance/droneubuntu2204:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-12', CXXSTD: '17,20', ADDRMD: '32,64' },
|
||||
"g++-12-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 22.04 GCC 12 32/64",
|
||||
"cppalliance/droneubuntu2204:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-12', CXXSTD: '2b', ADDRMD: '32,64' },
|
||||
"g++-12-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.04 GCC 13 32/64 UBSAN C++11-14",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-13', CXXSTD: '11,14', ADDRMD: '32,64' } + ubsan,
|
||||
"g++-13-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.04 GCC 13 32/64 UBSAN C++17-20",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-13', CXXSTD: '17,20', ADDRMD: '32,64' } + ubsan,
|
||||
"g++-13-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.04 GCC 13 32/64 UBSAN",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-13', CXXSTD: '2b', ADDRMD: '32,64' } + ubsan,
|
||||
"g++-13-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.04 GCC 13 32 ASAN C++11-14",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-13', CXXSTD: '11,14', ADDRMD: '32' } + asan,
|
||||
"g++-13-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.04 GCC 13 32 ASAN C++17-20",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-13', CXXSTD: '17,20', ADDRMD: '32' } + asan,
|
||||
"g++-13-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.04 GCC 13 32 ASAN",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-13', CXXSTD: '2b', ADDRMD: '32' } + asan,
|
||||
"g++-13-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 24.04 GCC 14 UBSAN C++11-14",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-14', CXXSTD: '11,14' } + ubsan,
|
||||
"g++-14-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 24.04 GCC 14 UBSAN C++17-20",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-14', CXXSTD: '17,20' } + ubsan,
|
||||
"g++-14-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 24.04 GCC 14 UBSAN",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-14', CXXSTD: '2b' } + ubsan,
|
||||
"g++-14-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 24.04 GCC 14 ASAN C++11-14",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-14', CXXSTD: '11,14' } + asan,
|
||||
"g++-14-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 24.04 GCC 14 ASAN C++17-20",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-14', CXXSTD: '17,20' } + asan,
|
||||
"g++-14-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 24.04 GCC 14 ASAN",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'gcc', COMPILER: 'g++-14', CXXSTD: '2b' } + asan,
|
||||
"g++-14-multilib",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 16.04 Clang 3.5",
|
||||
"cppalliance/droneubuntu1604:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-3.5', CXXSTD: '11' },
|
||||
"clang-3.5",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 16.04 Clang 3.6",
|
||||
"cppalliance/droneubuntu1604:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-3.6', CXXSTD: '11,14' },
|
||||
"clang-3.6",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 16.04 Clang 3.7",
|
||||
"cppalliance/droneubuntu1604:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-3.7', CXXSTD: '11,14' },
|
||||
"clang-3.7",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 16.04 Clang 3.8",
|
||||
"cppalliance/droneubuntu1604:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-3.8', CXXSTD: '11,14' },
|
||||
"clang-3.8",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 18.04 Clang 3.9",
|
||||
"cppalliance/droneubuntu1804:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-3.9', CXXSTD: '11,14' },
|
||||
"clang-3.9",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 18.04 Clang 4.0",
|
||||
"cppalliance/droneubuntu1804:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-4.0', CXXSTD: '11,14' },
|
||||
"clang-4.0",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 18.04 Clang 5.0",
|
||||
"cppalliance/droneubuntu1804:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-5.0', CXXSTD: '11,14' },
|
||||
"clang-5.0",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 18.04 Clang 6.0",
|
||||
"cppalliance/droneubuntu1804:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-6.0', CXXSTD: '11,14,17' },
|
||||
"clang-6.0",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 Clang 7",
|
||||
"cppalliance/droneubuntu2004:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-7', CXXSTD: '11,14,17' },
|
||||
"clang-7",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 Clang 8",
|
||||
"cppalliance/droneubuntu2004:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-8', CXXSTD: '11,14,17' },
|
||||
"clang-8",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 Clang 9",
|
||||
"cppalliance/droneubuntu2004:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-9', CXXSTD: '11,14,17,2a' },
|
||||
"clang-9",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 Clang 10",
|
||||
"cppalliance/droneubuntu2004:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-10', CXXSTD: '11,14,17,2a' },
|
||||
"clang-10",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 Clang 11",
|
||||
"cppalliance/droneubuntu2004:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-11', CXXSTD: '11,14,17,2a' },
|
||||
"clang-11",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 20.04 Clang 12",
|
||||
"cppalliance/droneubuntu2004:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-12', CXXSTD: '11,14,17,2a' },
|
||||
"clang-12",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 22.04 Clang 13",
|
||||
"cppalliance/droneubuntu2204:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-13', CXXSTD: '11,14,17,20' },
|
||||
"clang-13",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 22.04 Clang 14",
|
||||
"cppalliance/droneubuntu2204:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-14', CXXSTD: '11,14,17,20,2b' },
|
||||
"clang-14",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 22.04 Clang 15",
|
||||
"cppalliance/droneubuntu2204:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-15', CXXSTD: '11,14,17,20,2b' },
|
||||
"clang-15",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.04 Clang 16",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-16', CXXSTD: '11,14,17,20,2b' },
|
||||
"clang-16",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.10 Clang 17 UBSAN",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-17', CXXSTD: '11,14,17,20,2b' } + ubsan,
|
||||
"clang-17",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 23.10 Clang 17 ASAN",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-17', CXXSTD: '11,14,17,20,2b' } + asan,
|
||||
"clang-17",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 24.04 Clang 18 UBSAN",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-18', CXXSTD: '11,14,17,20,2b' } + ubsan,
|
||||
"clang-18",
|
||||
),
|
||||
|
||||
linux_pipeline(
|
||||
"Linux 24.04 Clang 18 ASAN",
|
||||
"cppalliance/droneubuntu2404:1",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++-18', CXXSTD: '11,14,17,20,2b' } + asan,
|
||||
"clang-18",
|
||||
),
|
||||
|
||||
macos_pipeline(
|
||||
"MacOS 10.15 Xcode 12.2 UBSAN (11,14)",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++', CXXSTD: '11,14' } + ubsan,
|
||||
),
|
||||
|
||||
macos_pipeline(
|
||||
"MacOS 10.15 Xcode 12.2 UBSAN (17,2a)",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++', CXXSTD: '17,2a' } + ubsan,
|
||||
),
|
||||
|
||||
macos_pipeline(
|
||||
"MacOS 10.15 Xcode 12.2 ASAN (11,14)",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++', CXXSTD: '11,14' } + asan,
|
||||
),
|
||||
|
||||
macos_pipeline(
|
||||
"MacOS 10.15 Xcode 12.2 ASAN (17,2a)",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++', CXXSTD: '17,2a' } + asan,
|
||||
),
|
||||
|
||||
macos_pipeline(
|
||||
"MacOS 12.4 Xcode 13.4.1 UBSAN",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++', CXXSTD: '11,14,17,20,2b', LINK: 'static' } + ubsan,
|
||||
xcode_version = "13.4.1", osx_version = "monterey", arch = "arm64",
|
||||
),
|
||||
|
||||
macos_pipeline(
|
||||
"MacOS 12.4 Xcode 13.4.1 ASAN",
|
||||
{ TOOLSET: 'clang', COMPILER: 'clang++', CXXSTD: '11,14,17,20,2b' } + asan,
|
||||
xcode_version = "13.4.1", osx_version = "monterey", arch = "arm64",
|
||||
),
|
||||
|
||||
windows_pipeline(
|
||||
"Windows VS2015 msvc-14.0",
|
||||
"cppalliance/dronevs2015",
|
||||
{ TOOLSET: 'msvc-14.0', CXXSTD: '14,latest', B2_DONT_EMBED_MANIFEST: '1' },
|
||||
),
|
||||
|
||||
windows_pipeline(
|
||||
"Windows VS2017 msvc-14.1",
|
||||
"cppalliance/dronevs2017",
|
||||
{ TOOLSET: 'msvc-14.1', CXXSTD: '14,17,latest' },
|
||||
),
|
||||
|
||||
windows_pipeline(
|
||||
"Windows VS2019 msvc-14.2",
|
||||
"cppalliance/dronevs2019",
|
||||
{ TOOLSET: 'msvc-14.2', CXXSTD: '14,17,20,latest' },
|
||||
),
|
||||
|
||||
windows_pipeline(
|
||||
"Windows VS2022 msvc-14.3",
|
||||
"cppalliance/dronevs2022:1",
|
||||
{ TOOLSET: 'msvc-14.3', CXXSTD: '14,17,20,latest' },
|
||||
),
|
||||
]
|
||||
@@ -1,23 +0,0 @@
|
||||
@REM Copyright 2022 Peter Dimov
|
||||
@REM Distributed under the Boost Software License, Version 1.0.
|
||||
@REM https://www.boost.org/LICENSE_1_0.txt
|
||||
|
||||
@ECHO ON
|
||||
|
||||
set LIBRARY=%1
|
||||
set DRONE_BUILD_DIR=%CD%
|
||||
|
||||
set BOOST_BRANCH=develop
|
||||
if "%DRONE_BRANCH%" == "master" set BOOST_BRANCH=master
|
||||
cd ..
|
||||
git clone -b %BOOST_BRANCH% --depth 1 https://github.com/boostorg/boost.git boost-root
|
||||
cd boost-root
|
||||
git submodule update --init tools/boostdep
|
||||
xcopy /s /e /q %DRONE_BUILD_DIR% libs\%LIBRARY%\
|
||||
python tools/boostdep/depinst/depinst.py -I examples %LIBRARY%
|
||||
cmd /c bootstrap
|
||||
b2 -d0 headers
|
||||
|
||||
if not "%CXXSTD%" == "" set CXXSTD=cxxstd=%CXXSTD%
|
||||
if not "%ADDRMD%" == "" set ADDRMD=address-model=%ADDRMD%
|
||||
b2 -j3 libs/%LIBRARY%/test toolset=%TOOLSET% %CXXSTD% %ADDRMD% variant=debug,release embed-manifest-via=linker
|
||||
@@ -1,25 +0,0 @@
|
||||
#!/bin/bash
|
||||
|
||||
# Copyright 2022 Peter Dimov
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# https://www.boost.org/LICENSE_1_0.txt
|
||||
|
||||
set -ex
|
||||
export PATH=~/.local/bin:/usr/local/bin:$PATH
|
||||
|
||||
DRONE_BUILD_DIR=$(pwd)
|
||||
|
||||
BOOST_BRANCH=develop
|
||||
if [ "$DRONE_BRANCH" = "master" ]; then BOOST_BRANCH=master; fi
|
||||
|
||||
cd ..
|
||||
git clone -b $BOOST_BRANCH --depth 1 https://github.com/boostorg/boost.git boost-root
|
||||
cd boost-root
|
||||
git submodule update --init tools/boostdep
|
||||
cp -r $DRONE_BUILD_DIR/* libs/$LIBRARY
|
||||
python tools/boostdep/depinst/depinst.py -I examples $LIBRARY
|
||||
./bootstrap.sh
|
||||
./b2 -d0 headers
|
||||
|
||||
echo "using $TOOLSET : : $COMPILER ;" > ~/user-config.jam
|
||||
./b2 -j3 libs/$LIBRARY/test toolset=$TOOLSET cxxstd=$CXXSTD variant=debug,release ${ADDRMD:+address-model=$ADDRMD} ${UBSAN:+undefined-sanitizer=norecover debug-symbols=on} ${ASAN:+address-sanitizer=norecover debug-symbols=on} ${LINKFLAGS:+linkflags=$LINKFLAGS} ${LINK:+link=$LINK}
|
||||
@@ -1,325 +0,0 @@
|
||||
name: CI
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
push:
|
||||
branches:
|
||||
- master
|
||||
- develop
|
||||
- feature/**
|
||||
- fix/**
|
||||
|
||||
env:
|
||||
UBSAN_OPTIONS: print_stacktrace=1
|
||||
ACTIONS_ALLOW_USE_UNSECURE_NODE_VERSION: true
|
||||
|
||||
jobs:
|
||||
posix:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- toolset: gcc-4.8
|
||||
cxxstd: "11"
|
||||
container: ubuntu:18.04
|
||||
os: ubuntu-latest
|
||||
install: g++-4.8-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-5
|
||||
cxxstd: "11,14,1z"
|
||||
container: ubuntu:18.04
|
||||
os: ubuntu-latest
|
||||
install: g++-5-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-6
|
||||
cxxstd: "11,14,1z"
|
||||
container: ubuntu:18.04
|
||||
os: ubuntu-latest
|
||||
install: g++-6-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-7
|
||||
cxxstd: "11,14,17"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: g++-7-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-8
|
||||
cxxstd: "11,14,17,2a"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: g++-8-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-9
|
||||
cxxstd: "11,14,17,2a"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: g++-9-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-10
|
||||
cxxstd: "11,14,17,2a"
|
||||
os: ubuntu-22.04
|
||||
install: g++-10-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-11
|
||||
cxxstd: "11,14,17,20"
|
||||
os: ubuntu-22.04
|
||||
install: g++-11-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-12
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
os: ubuntu-22.04
|
||||
install: g++-12-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-13
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
os: ubuntu-24.04
|
||||
install: g++-13-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-14
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
os: ubuntu-24.04
|
||||
install: g++-14-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-15
|
||||
cxxstd: "11,14,17,20,23,2c"
|
||||
container: ubuntu:26.04
|
||||
os: ubuntu-latest
|
||||
install: g++-15-multilib
|
||||
address-model: 32,64
|
||||
- toolset: gcc-16
|
||||
cxxstd: "11,14,17,20,23,2c"
|
||||
container: ubuntu:26.04
|
||||
os: ubuntu-latest
|
||||
install: g++-16-multilib
|
||||
address-model: 32,64
|
||||
- toolset: clang
|
||||
compiler: clang++-3.9
|
||||
cxxstd: "11,14"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: clang-3.9
|
||||
- toolset: clang
|
||||
compiler: clang++-4.0
|
||||
cxxstd: "11,14"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: clang-4.0
|
||||
- toolset: clang
|
||||
compiler: clang++-5.0
|
||||
cxxstd: "11,14"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: clang-5.0
|
||||
- toolset: clang
|
||||
compiler: clang++-6.0
|
||||
cxxstd: "11,14,17"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: clang-6.0
|
||||
- toolset: clang
|
||||
compiler: clang++-7
|
||||
cxxstd: "11,14,17"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: clang-7
|
||||
- toolset: clang
|
||||
compiler: clang++-8
|
||||
cxxstd: "11,14,17"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: clang-8
|
||||
- toolset: clang
|
||||
compiler: clang++-9
|
||||
cxxstd: "11,14,17,2a"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: clang-9
|
||||
- toolset: clang
|
||||
compiler: clang++-10
|
||||
cxxstd: "11,14,17,2a"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: clang-10
|
||||
- toolset: clang
|
||||
compiler: clang++-11
|
||||
cxxstd: "11,14,17,2a"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: clang-11
|
||||
- toolset: clang
|
||||
compiler: clang++-12
|
||||
cxxstd: "11,14,17,20"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: clang-12
|
||||
- toolset: clang
|
||||
compiler: clang++-13
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:22.04
|
||||
os: ubuntu-latest
|
||||
install: clang-13
|
||||
- toolset: clang
|
||||
compiler: clang++-14
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:22.04
|
||||
os: ubuntu-latest
|
||||
install: clang-14
|
||||
- toolset: clang
|
||||
compiler: clang++-15
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:22.04
|
||||
os: ubuntu-latest
|
||||
install: clang-15
|
||||
- toolset: clang
|
||||
compiler: clang++-16
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:24.04
|
||||
os: ubuntu-latest
|
||||
install: clang-16
|
||||
- toolset: clang
|
||||
compiler: clang++-17
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:24.04
|
||||
os: ubuntu-latest
|
||||
install: clang-17
|
||||
- toolset: clang
|
||||
compiler: clang++-18
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:24.04
|
||||
os: ubuntu-latest
|
||||
install: clang-18
|
||||
- toolset: clang
|
||||
compiler: clang++-19
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:24.04
|
||||
os: ubuntu-latest
|
||||
install: clang-19
|
||||
- toolset: clang
|
||||
compiler: clang++-20
|
||||
cxxstd: "11,14,17,20,23,2c"
|
||||
container: ubuntu:24.04
|
||||
os: ubuntu-latest
|
||||
install: clang-20
|
||||
- toolset: clang
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
os: macos-14
|
||||
- toolset: clang
|
||||
cxxstd: "11,14,17,20,23,2c"
|
||||
os: macos-15
|
||||
- toolset: clang
|
||||
cxxstd: "11,14,17,20,23,2c"
|
||||
os: macos-26
|
||||
|
||||
runs-on: ${{matrix.os}}
|
||||
container:
|
||||
image: ${{matrix.container}}
|
||||
volumes:
|
||||
- /node20217:/node20217:rw,rshared
|
||||
- ${{ startsWith(matrix.container, 'ubuntu:1') && '/node20217:/__e/node20:ro,rshared' || ' ' }}
|
||||
|
||||
defaults:
|
||||
run:
|
||||
shell: bash
|
||||
|
||||
steps:
|
||||
- name: Setup container environment
|
||||
if: matrix.container
|
||||
run: |
|
||||
apt-get update
|
||||
apt-get -y install sudo python3 git g++ curl xz-utils
|
||||
if [[ "${{matrix.container}}" == "ubuntu:1"* ]]; then
|
||||
# Node 20 doesn't work with Ubuntu 16/18 glibc: https://github.com/actions/checkout/issues/1590
|
||||
curl -sL https://archives.boost.io/misc/node/node-v20.9.0-linux-x64-glibc-217.tar.xz | tar -xJ --strip-components 1 -C /node20217
|
||||
fi
|
||||
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install packages
|
||||
if: matrix.install
|
||||
run: |
|
||||
sudo apt-get update
|
||||
sudo apt-get -y install ${{matrix.install}}
|
||||
|
||||
- name: Setup Boost
|
||||
run: |
|
||||
echo GITHUB_REPOSITORY: $GITHUB_REPOSITORY
|
||||
LIBRARY=${GITHUB_REPOSITORY#*/}
|
||||
echo LIBRARY: $LIBRARY
|
||||
echo "LIBRARY=$LIBRARY" >> $GITHUB_ENV
|
||||
echo GITHUB_BASE_REF: $GITHUB_BASE_REF
|
||||
echo GITHUB_REF: $GITHUB_REF
|
||||
REF=${GITHUB_BASE_REF:-$GITHUB_REF}
|
||||
REF=${REF#refs/heads/}
|
||||
echo REF: $REF
|
||||
BOOST_BRANCH=develop && [ "$REF" == "master" ] && BOOST_BRANCH=master || true
|
||||
echo BOOST_BRANCH: $BOOST_BRANCH
|
||||
cd ..
|
||||
git clone -b $BOOST_BRANCH --depth 1 https://github.com/boostorg/boost.git boost-root
|
||||
cd boost-root
|
||||
cp -r $GITHUB_WORKSPACE/* libs/$LIBRARY
|
||||
git submodule update --init tools/boostdep
|
||||
python3 tools/boostdep/depinst/depinst.py -I example --git_args "--jobs 3" $LIBRARY
|
||||
./bootstrap.sh
|
||||
./b2 -d0 headers
|
||||
|
||||
- name: Create user-config.jam
|
||||
if: matrix.compiler
|
||||
run: |
|
||||
echo "using ${{matrix.toolset}} : : ${{matrix.compiler}} ;" > ~/user-config.jam
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
cd ../boost-root
|
||||
export ADDRMD=${{matrix.address-model}}
|
||||
./b2 -j3 libs/$LIBRARY/test toolset=${{matrix.toolset}} cxxstd=${{matrix.cxxstd}} ${ADDRMD:+address-model=$ADDRMD} variant=debug,release
|
||||
|
||||
windows:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- toolset: msvc-14.3
|
||||
cxxstd: "14,17,20,latest"
|
||||
addrmd: 32,64
|
||||
os: windows-2022
|
||||
- toolset: clang-win
|
||||
cxxstd: "14,17,latest"
|
||||
addrmd: 32,64
|
||||
os: windows-2022
|
||||
- toolset: gcc
|
||||
cxxstd: "11,14,17,2a"
|
||||
addrmd: 64
|
||||
os: windows-2022
|
||||
|
||||
runs-on: ${{matrix.os}}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Setup Boost
|
||||
shell: cmd
|
||||
run: |
|
||||
echo GITHUB_REPOSITORY: %GITHUB_REPOSITORY%
|
||||
for /f %%i in ("%GITHUB_REPOSITORY%") do set LIBRARY=%%~nxi
|
||||
echo LIBRARY: %LIBRARY%
|
||||
echo LIBRARY=%LIBRARY%>>%GITHUB_ENV%
|
||||
echo GITHUB_BASE_REF: %GITHUB_BASE_REF%
|
||||
echo GITHUB_REF: %GITHUB_REF%
|
||||
if "%GITHUB_BASE_REF%" == "" set GITHUB_BASE_REF=%GITHUB_REF%
|
||||
set BOOST_BRANCH=develop
|
||||
for /f %%i in ("%GITHUB_BASE_REF%") do if "%%~nxi" == "master" set BOOST_BRANCH=master
|
||||
echo BOOST_BRANCH: %BOOST_BRANCH%
|
||||
cd ..
|
||||
git clone -b %BOOST_BRANCH% --depth 1 https://github.com/boostorg/boost.git boost-root
|
||||
cd boost-root
|
||||
xcopy /s /e /q %GITHUB_WORKSPACE% libs\%LIBRARY%\
|
||||
git submodule update --init tools/boostdep
|
||||
python tools/boostdep/depinst/depinst.py -I example --git_args "--jobs 3" %LIBRARY%
|
||||
cmd /c bootstrap
|
||||
b2 -d0 headers
|
||||
|
||||
- name: Run tests
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root
|
||||
b2 -j3 libs/%LIBRARY%/test toolset=${{matrix.toolset}} cxxstd=${{matrix.cxxstd}} address-model=${{matrix.addrmd}} variant=debug,release embed-manifest-via=linker
|
||||
+1
-3
@@ -1,4 +1,4 @@
|
||||
# Copyright 2003-2019 Joaquín M López Muñoz.
|
||||
# Copyright 2003-2018 Joaquín M López Muñoz.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -10,8 +10,6 @@ sudo: false
|
||||
language: cpp
|
||||
|
||||
os: linux
|
||||
|
||||
dist: trusty
|
||||
|
||||
branches:
|
||||
only:
|
||||
|
||||
@@ -1,38 +0,0 @@
|
||||
# Generated by `boostdep --cmake multi_index`
|
||||
# Copyright 2020 Peter Dimov
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# https://www.boost.org/LICENSE_1_0.txt
|
||||
|
||||
cmake_minimum_required(VERSION 3.8...3.16)
|
||||
|
||||
project(boost_multi_index VERSION "${BOOST_SUPERPROJECT_VERSION}" LANGUAGES CXX)
|
||||
|
||||
add_library(boost_multi_index INTERFACE)
|
||||
add_library(Boost::multi_index ALIAS boost_multi_index)
|
||||
target_compile_features(boost_multi_index INTERFACE cxx_std_11)
|
||||
|
||||
target_include_directories(boost_multi_index INTERFACE include)
|
||||
|
||||
target_link_libraries(boost_multi_index
|
||||
INTERFACE
|
||||
Boost::assert
|
||||
Boost::bind
|
||||
Boost::config
|
||||
Boost::container_hash
|
||||
Boost::core
|
||||
Boost::integer
|
||||
Boost::mp11
|
||||
Boost::preprocessor
|
||||
Boost::smart_ptr
|
||||
Boost::throw_exception
|
||||
Boost::tuple
|
||||
Boost::type_traits
|
||||
Boost::utility
|
||||
)
|
||||
|
||||
if(BUILD_TESTING AND EXISTS "${CMAKE_CURRENT_SOURCE_DIR}/test/CMakeLists.txt")
|
||||
|
||||
add_subdirectory(test)
|
||||
|
||||
endif()
|
||||
|
||||
@@ -1,48 +1,10 @@
|
||||
# Boost Multi-index Containers Library
|
||||
|
||||
[](https://github.com/boostorg/multi_index/tree/master) [](https://github.com/boostorg/multi_index/actions/workflows/ci.yml) [](https://drone.cpp.al/boostorg/multi_index) [](https://pdimov.github.io/boostdep-report/master/multi_index.html) [](https://www.boost.org/doc/libs/master/libs/multi_index) [](https://regression.boost.org/master/developer/multi_index.html)<br/>
|
||||
[](https://github.com/boostorg/multi_index/tree/develop) [](https://github.com/boostorg/multi_index/actions/workflows/ci.yml) [](https://drone.cpp.al/boostorg/multi_index) [](https://pdimov.github.io/boostdep-report/develop/multi_index.html) [](https://www.boost.org/doc/libs/develop/libs/multi_index) [](https://regression.boost.org/develop/developer/multi_index.html)<br/>
|
||||
[](https://www.boost.org/users/license.html) <img alt="C++11 required" src="https://img.shields.io/badge/standard-C%2b%2b11-blue.svg"> <img alt="Header-only library" src="https://img.shields.io/badge/build-header--only-blue.svg">
|
||||
Branch | Travis | AppVeyor | Regression tests
|
||||
---------|--------|----------|-----------------
|
||||
develop | [](https://travis-ci.com/boostorg/multi_index) | [](https://ci.appveyor.com/project/joaquintides/multi-index) | [](https://www.boost.org/development/tests/develop/developer/multi_index.html)
|
||||
master | [](https://travis-ci.com/boostorg/multi_index) | [](https://ci.appveyor.com/project/joaquintides/multi-index) | [](https://www.boost.org/development/tests/master/developer/multi_index.html)
|
||||
|
||||
[Boost.MultiIndex](http://boost.org/libs/multi_index) provides a class template
|
||||
named `multi_index_container` which enables the construction of containers
|
||||
maintaining one or more indices with different sorting and access semantics.
|
||||
|
||||
## Learn about Boost.MultiIndex
|
||||
|
||||
* [Online documentation](https://boost.org/libs/multi_index)
|
||||
|
||||
## Install Boost.MultiIndex
|
||||
|
||||
* [Download Boost](https://www.boost.org/users/download/) and you're ready to go (this is a header-only library requiring no building).
|
||||
* Using Conan 2: In case you don't have it yet, add an entry for Boost in your `conanfile.txt` (the example requires at least Boost 1.86):
|
||||
```
|
||||
[requires]
|
||||
boost/[>=1.86.0]
|
||||
```
|
||||
<ul>If you're not using any compiled Boost library, the following will skip building altogether:</ul>
|
||||
|
||||
```
|
||||
[options]
|
||||
boost:header_only=True
|
||||
```
|
||||
* Using vcpkg: Execute the command
|
||||
```
|
||||
vcpkg install boost-multi-index
|
||||
```
|
||||
* Using CMake: [Boost CMake support infrastructure](https://github.com/boostorg/cmake)
|
||||
allows you to use CMake directly to download, build and consume all of Boost or
|
||||
some specific libraries.
|
||||
|
||||
## Support
|
||||
|
||||
* Join the **#boost** discussion group at [cpplang.slack.com](https://cpplang.slack.com/)
|
||||
([ask for an invite](https://cppalliance.org/slack/) if you’re not a member of this workspace yet)
|
||||
* Ask in the [Boost Users mailing list](https://lists.boost.org/mailman/listinfo.cgi/boost-users)
|
||||
(add the `[multi_index]` tag at the beginning of the subject line)
|
||||
* [File an issue](https://github.com/boostorg/multi_index/issues)
|
||||
|
||||
## Contribute
|
||||
|
||||
* [Pull requests](https://github.com/boostorg/multi_index/pulls) against **develop** branch are most welcome.
|
||||
Note that by submitting patches you agree to license your modifications under the [Boost Software License, Version 1.0](http://www.boost.org/LICENSE_1_0.txt).
|
||||
|
||||
+3
-3
@@ -1,4 +1,4 @@
|
||||
# Copyright 2003-2021 Joaquín M López Muñoz.
|
||||
# Copyright 2003-2019 Joaquín M López Muñoz.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,7 +15,7 @@ branches:
|
||||
environment:
|
||||
matrix:
|
||||
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015
|
||||
TOOLSET: msvc-14.0
|
||||
TOOLSET: msvc-9.0,msvc-10.0,msvc-11.0,msvc-12.0,msvc-14.0
|
||||
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017
|
||||
TOOLSET: msvc-14.1
|
||||
CXXSTD: 14,17
|
||||
@@ -34,4 +34,4 @@ build: off
|
||||
|
||||
test_script:
|
||||
- if not "%CXXSTD%" == "" set CXXSTD=cxxstd=%CXXSTD%
|
||||
- b2 address-model=32 libs/multi_index/test toolset=%TOOLSET% %CXXSTD%
|
||||
- b2 libs/multi_index/test toolset=%TOOLSET% %CXXSTD%
|
||||
@@ -1,35 +0,0 @@
|
||||
# Copyright René Ferdinand Rivera Morell 2023-2024
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
|
||||
require-b2 5.2 ;
|
||||
|
||||
constant boost_dependencies :
|
||||
/boost/assert//boost_assert
|
||||
/boost/bind//boost_bind
|
||||
/boost/config//boost_config
|
||||
/boost/container_hash//boost_container_hash
|
||||
/boost/core//boost_core
|
||||
/boost/integer//boost_integer
|
||||
/boost/mp11//boost_mp11
|
||||
/boost/preprocessor//boost_preprocessor
|
||||
/boost/smart_ptr//boost_smart_ptr
|
||||
/boost/throw_exception//boost_throw_exception
|
||||
/boost/tuple//boost_tuple
|
||||
/boost/type_traits//boost_type_traits
|
||||
/boost/utility//boost_utility ;
|
||||
|
||||
project /boost/multi_index
|
||||
: common-requirements
|
||||
<include>include
|
||||
;
|
||||
|
||||
explicit
|
||||
[ alias boost_multi_index : : : : <library>$(boost_dependencies) ]
|
||||
[ alias all : boost_multi_index example perf test ]
|
||||
;
|
||||
|
||||
call-if : boost-library multi_index
|
||||
;
|
||||
|
||||
@@ -0,0 +1,390 @@
|
||||
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0.1 Transitional//EN">
|
||||
|
||||
<html>
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
|
||||
<title>Boost.MultiIndex Documentation - Compiler specifics</title>
|
||||
<link rel="stylesheet" href="style.css" type="text/css">
|
||||
<link rel="start" href="index.html">
|
||||
<link rel="prev" href="reference/key_extraction.html">
|
||||
<link rel="up" href="index.html">
|
||||
<link rel="next" href="performance.html">
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h1><img src="../../../boost.png" alt="boost.png (6897 bytes)" align=
|
||||
"middle" width="277" height="86">Boost.MultiIndex Compiler specifics</h1>
|
||||
|
||||
<div class="prev_link"><a href="reference/key_extraction.html"><img src="prev.gif" alt="key extraction" border="0"><br>
|
||||
Key extraction
|
||||
</a></div>
|
||||
<div class="up_link"><a href="index.html"><img src="up.gif" alt="index" border="0"><br>
|
||||
Index
|
||||
</a></div>
|
||||
<div class="next_link"><a href="performance.html"><img src="next.gif" alt="performance" border="0"><br>
|
||||
Performance
|
||||
</a></div><br clear="all" style="clear: all;">
|
||||
|
||||
<hr>
|
||||
|
||||
<p>
|
||||
Boost.MultiIndex utilizes some C++11 capabilities but is also equipped
|
||||
to work reasonably well in decent C++03-compliant environments.
|
||||
We list some of the possible limitations along with suitable workarounds when available.
|
||||
</p>
|
||||
|
||||
<h2>Contents</h2>
|
||||
|
||||
<ul>
|
||||
<li><a href="#move">Move semantics</a></li>
|
||||
<li><a href="#emplace">Emplace functions</a></li>
|
||||
<li><a href="#initializer_list">Initializer lists</a></li>
|
||||
<li><a href="#tuple">Tuples</a></li>
|
||||
<li><a href="#symbol_reduction">Reduction of symbol name lengths</a>
|
||||
<ul>
|
||||
<li><a href="#argument_limitation">Limitation of maximum number of arguments</a></li>
|
||||
<li><a href="#type_hiding">Type hiding</a></li>
|
||||
</ul>
|
||||
</li>
|
||||
<li><a href="#legacy">Legacy compilers</a></li>
|
||||
</ul>
|
||||
|
||||
<h2><a name="move">Move semantics</a></h2>
|
||||
|
||||
<p>
|
||||
Boost.MultiIndex uses <a href="../../../doc/html/move.html">Boost.Move</a>
|
||||
to support compilers without rvalue references. In such scenarios, taking
|
||||
advantage of <code>multi_index_container<Value></code> capabilities for
|
||||
increased efficiency in insertion and handling of moveable-only elements will
|
||||
require that <code>Value</code> be suitably instrumented.
|
||||
</p>
|
||||
|
||||
<h2><a name="emplace">Emplace functions</a></h2>
|
||||
|
||||
<p>
|
||||
In compilers without variadic template support, Boost.MultiIndex emplace
|
||||
functions emulate this missing functionality by accepting up to
|
||||
<code>BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS</code>
|
||||
construction arguments that are internally forwarded with
|
||||
<a href="../../../doc/html/move.html">Boost.Move</a>:
|
||||
only constant lvalue references and rvalues are permitted as construction arguments
|
||||
in such case.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
<code>BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS</code>, which by default is 5, can
|
||||
be globally defined by the user to a different value.
|
||||
</p>
|
||||
|
||||
<h2><a name="initializer_list">Initializer lists</a></h2>
|
||||
|
||||
<p>
|
||||
No transparent emulation of this functionality can be provided in the absence of
|
||||
<code>std::initializer_list</code>: consider
|
||||
<a href="../../../libs/assign/index.html">Boost.Assign</a> as a
|
||||
possible replacement.
|
||||
</p>
|
||||
|
||||
<h2><a name="tuple">Tuples</a></h2>
|
||||
|
||||
<p>
|
||||
Everywhere where <code>std::tuple</code>s are used in the library interface,
|
||||
<code>boost::tuple</code>s can be resorted to in their place. The converse, however,
|
||||
is not true.
|
||||
</p>
|
||||
|
||||
<h2><a name="symbol_reduction">Reduction of symbol name lengths</a></h2>
|
||||
|
||||
<p>
|
||||
The types generated on the instantiations of <code>multi_index_container</code>s
|
||||
typically produce very long symbol names, sometimes beyond the internal limits
|
||||
of some compilers. There are several techniques to shorten generated symbol
|
||||
names: these techniques have also the beneficial side effect that resulting error
|
||||
messages are more readable.
|
||||
</p>
|
||||
|
||||
<h3><a name="argument_limitation">Limitation of maximum number of arguments</a></h3>
|
||||
|
||||
<p>
|
||||
The class templates <a href="reference/indices.html#indexed_by"><code>indexed_by</code></a>,
|
||||
<a href="reference/indices.html#tag"><code>tag</code></a> and
|
||||
<a href="reference/key_extraction.html#composite_key"><code>composite_key</code></a>
|
||||
accept a variable number of arguments whose maximum number is limited by
|
||||
internal macros. Even non-used arguments contribute to the final types,
|
||||
so manually adjusting the corresponding macros can result in a modest reduction
|
||||
of symbol names.
|
||||
</p>
|
||||
|
||||
<p align="center">
|
||||
<table cellspacing="0">
|
||||
<caption><b>Limiting maximum number of arguments of some class templates
|
||||
of Boost.MultiIndex.</b></caption>
|
||||
<tr>
|
||||
<th>class template</th>
|
||||
<th>limiting macro</th>
|
||||
<th>default value</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"> <code>indexed_by</code> </td>
|
||||
<td align="center"> <code>BOOST_MULTI_INDEX_LIMIT_INDEXED_BY_SIZE</code> </td>
|
||||
<td align="center">20</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td align="center"> <code>tag</code> </td>
|
||||
<td align="center"> <code>BOOST_MULTI_INDEX_LIMIT_TAG_SIZE</code> </td>
|
||||
<td align="center">20</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td align="center"> <code>composite_key</code> </td>
|
||||
<td align="center"> <code>BOOST_MULTI_INDEX_LIMIT_COMPOSITE_KEY_SIZE</code> </td>
|
||||
<td align="center">10</td>
|
||||
</tr>
|
||||
</table>
|
||||
</p>
|
||||
|
||||
<h3><a name="type_hiding">Type hiding</a></h3>
|
||||
|
||||
<p>
|
||||
Consider a typical instantiation of <code>multi_index_container</code>:
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=keyword>typedef</span> <span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=identifier>employee</span><span class=special>,</span>
|
||||
<span class=identifier>indexed_by</span><span class=special><</span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=identifier>employee</span><span class=special>></span> <span class=special>>,</span>
|
||||
<span class=identifier>ordered_non_unique</span><span class=special><</span><span class=identifier>member</span><span class=special><</span><span class=identifier>employee</span><span class=special>,</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>string</span><span class=special>,&</span><span class=identifier>employee</span><span class=special>::</span><span class=identifier>name</span><span class=special>></span> <span class=special>>,</span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>member</span><span class=special><</span><span class=identifier>employee</span><span class=special>,</span><span class=keyword>int</span><span class=special>,&</span><span class=identifier>employee</span><span class=special>::</span><span class=identifier>ssnumber</span><span class=special>></span> <span class=special>></span>
|
||||
<span class=special>></span>
|
||||
<span class=special>></span> <span class=identifier>employee_set</span><span class=special>;</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
Then, for instance, the type <code>employee_set::nth_index<0>::type</code>
|
||||
resolves to the following in GCC:
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>detail</span><span class=special>::</span><span class=identifier>ordered_index</span><span class=special><</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>identity</span><span class=special><</span><span class=identifier>employee</span><span class=special>>,</span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>less</span><span class=special><</span><span class=identifier>employee</span><span class=special>>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>detail</span><span class=special>::</span><span class=identifier>nth_layer</span><span class=special><</span>
|
||||
<span class=number>1</span><span class=special>,</span> <span class=identifier>employee</span><span class=special>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>indexed_by</span><span class=special><</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>ordered_unique</span><span class=special><</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>identity</span><span class=special><</span><span class=identifier>employee</span><span class=special>>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span>
|
||||
<span class=special>>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>ordered_non_unique</span><span class=special><</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>member</span><span class=special><</span><span class=identifier>employee</span><span class=special>,</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>string</span><span class=special>,</span> <span class=special>&</span><span class=identifier>employee</span><span class=special>::</span><span class=identifier>name</span><span class=special>>,</span>
|
||||
<span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span>
|
||||
<span class=special>>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>ordered_unique</span><span class=special><</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>member</span><span class=special><</span><span class=identifier>employee</span><span class=special>,</span> <span class=keyword>int</span><span class=special>,</span> <span class=special>&</span><span class=identifier>employee</span><span class=special>::</span><span class=identifier>ssnumber</span><span class=special>>,</span>
|
||||
<span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span>
|
||||
<span class=special>>,</span>
|
||||
<span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span>
|
||||
<span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span>
|
||||
<span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>,</span> <span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span>
|
||||
<span class=special>>,</span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>allocator</span><span class=special><</span><span class=identifier>employee</span><span class=special>></span>
|
||||
<span class=special>>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>mpl</span><span class=special>::</span><span class=identifier>vector0</span><span class=special><</span><span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>detail</span><span class=special>::</span><span class=identifier>ordered_unique_tag</span>
|
||||
<span class=special>></span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
It can be seen that a significant portion of the type name is contributed by
|
||||
the <code>indexed_by<...></code> part, which is nothing but an expanded
|
||||
version of the index specifier list provided in the definition of
|
||||
<code>employee_set</code>. We can prevent this very long name from appearing
|
||||
in the final type by encapsulating it into another, shorter-named construct:
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=comment>// reducing symbol names through type hiding
|
||||
// type hide the index specifier list within employee_set_indices</span>
|
||||
|
||||
<span class=keyword>struct</span> <span class=identifier>employee_set_indices</span><span class=special>:</span>
|
||||
<span class=identifier>indexed_by</span><span class=special><</span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=identifier>employee</span><span class=special>></span> <span class=special>>,</span>
|
||||
<span class=identifier>ordered_non_unique</span><span class=special><</span><span class=identifier>member</span><span class=special><</span><span class=identifier>employee</span><span class=special>,</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>string</span><span class=special>,&</span><span class=identifier>employee</span><span class=special>::</span><span class=identifier>name</span><span class=special>></span> <span class=special>>,</span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>member</span><span class=special><</span><span class=identifier>employee</span><span class=special>,</span><span class=keyword>int</span><span class=special>,&</span><span class=identifier>employee</span><span class=special>::</span><span class=identifier>ssnumber</span><span class=special>></span> <span class=special>></span>
|
||||
<span class=special>></span>
|
||||
<span class=special>{};</span>
|
||||
|
||||
<span class=keyword>typedef</span> <span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=identifier>employee</span><span class=special>,</span>
|
||||
<span class=identifier>employee_set_indices</span>
|
||||
<span class=special>></span> <span class=identifier>employee_set</span><span class=special>;</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
<code>employee_set_indices</code> works as a conventional <code>typedef</code>
|
||||
in all respects, save for a detail: its name does not explicitly
|
||||
include the information contained in the <code>indexed_by</code> instantiation.
|
||||
Applying this technique, <code>employee_set::nth_index<0>::type</code>
|
||||
now becomes:
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>detail</span><span class=special>::</span><span class=identifier>ordered_index</span><span class=special><</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>identity</span><span class=special><</span><span class=identifier>employee</span><span class=special>>,</span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>less</span><span class=special><</span><span class=identifier>employee</span><span class=special>>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>detail</span><span class=special>::</span><span class=identifier>nth_layer</span><span class=special><</span>
|
||||
<span class=number>1</span><span class=special>,</span> <span class=identifier>employee</span><span class=special>,</span>
|
||||
<span class=identifier>employee_set_indices</span><span class=special>,</span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>allocator</span><span class=special><</span><span class=identifier>employee</span><span class=special>></span>
|
||||
<span class=special>>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>mpl</span><span class=special>::</span><span class=identifier>vector0</span><span class=special><</span><span class=identifier>mpl_</span><span class=special>::</span><span class=identifier>na</span><span class=special>>,</span>
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>multi_index</span><span class=special>::</span><span class=identifier>detail</span><span class=special>::</span><span class=identifier>ordered_unique_tag</span>
|
||||
<span class=special>></span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
which is considerably shorter than the original, and also more
|
||||
easily parsed by a human reader. Type hiding would not work if, instead of
|
||||
making <code>employee_set_indices</code> a derived <code>struct</code> of
|
||||
<code>indexed_by<...></code>, we had defined it as a <code>typedef</code>:
|
||||
<code>typedef</code>s are syntactic aliases and usually get expanded
|
||||
by the compiler before doing any further type handling.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
Type hiding techniques can also be applied to <code>composite_key</code> intantiations,
|
||||
which often contribute a great deal to symbol name lengths.
|
||||
</p>
|
||||
|
||||
<h2><a name="legacy">Legacy compilers</a></h2>
|
||||
|
||||
<p>
|
||||
Boost.MultiIndex support for legacy compilers is not actively kept, so if you happen
|
||||
to work with an old environment you might need to use a former version of the library.
|
||||
A table is provided of some legacy compilers along with the latest version of
|
||||
Boost.MultiIndex known to work for them (frequently with limitations as explained
|
||||
in the corresponding compiler specifics section.) If you successfully try one of those
|
||||
with newer versions of Boost.MultiIndex than stated here, please report back so that
|
||||
the information can be updated.
|
||||
</p>
|
||||
|
||||
<p align="center">
|
||||
<table cellspacing="0" cellpadding="5">
|
||||
<caption><b>Support for legacy compilers.</b></caption>
|
||||
<tr>
|
||||
<th>Compiler</th>
|
||||
<th>Latest known<br>compatible version</th>
|
||||
<th>Date</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Borland C++ Builder 6.4 through 2006, CodeGear C++Builder 2010</td>
|
||||
<td>Never worked with Boost.MultiIndex</td>
|
||||
<td></td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td>Comeau C/C++ 4.3.10.1 for Windows (VC++ 9.0 backend)</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_38_0/libs/multi_index/doc/compiler_specifics.html#comeau_43101_win_vc7_71">Boost 1.38</a></td>
|
||||
<td>February 2009</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Compaq C++ 6.5-042 through 7.1-006 for Tru64 UNIX</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_38_0/libs/multi_index/doc/compiler_specifics.html#compaq_65">Boost 1.38</a></td>
|
||||
<td>February 2009</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td>GCC 3.2 through 3.4</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_41_0/libs/multi_index/doc/compiler_specifics.html#gcc_32">Boost 1.41</a></td>
|
||||
<td>November 2009</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>HP aC++ A.06.12 through A.06.17 for HP-UX IA64</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_38_0/libs/multi_index/doc/compiler_specifics.html#acc_612_ia64">Boost 1.38</a></td>
|
||||
<td>February 2009</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td>HP aC++ A.03.80 through A.03.85 for HP-UX PA-RISC</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_38_0/libs/multi_index/doc/compiler_specifics.html#acc_380_pa_risc">Boost 1.38</a></td>
|
||||
<td>February 2009</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>IBM VisualAge C++ V6.0 for AIX</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_33_1/libs/multi_index/doc/compiler_specifics.html#va_60">Boost 1.33.1</a></td>
|
||||
<td>December 2006</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td>IBM XL C/C++ V9.0 through V10.1 for AIX</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_41_0/libs/multi_index/doc/compiler_specifics.html#xl_90">Boost 1.41</a></td>
|
||||
<td>November 2009</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Intel C++ Compiler for Linux 8.1 through 11.1</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_41_0/libs/multi_index/doc/compiler_specifics.html#intel_81_lin">Boost 1.41</a></td>
|
||||
<td>November 2009</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td>Intel C++ Compiler for Mac OS 9.1 through 11.0</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_41_0/libs/multi_index/doc/compiler_specifics.html#intel_91_mac">Boost 1.41</a></td>
|
||||
<td>November 2009</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Intel C++ Compiler for Windows 32-bit 8.0 through 11.1</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_41_0/libs/multi_index/doc/compiler_specifics.html#intel_80_win">Boost 1.41</a></td>
|
||||
<td>November 2009</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td>Intel C++ Compiler for Windows 64-bit 10.0 through 11.11</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_41_0/libs/multi_index/doc/compiler_specifics.html#intel_100_win64">Boost 1.41</a></td>
|
||||
<td>November 2009</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Metrowerks CodeWarrior 8.3</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_36_0/libs/multi_index/doc/compiler_specifics.html#cw_83">Boost 1.36</a></td>
|
||||
<td>August 2008</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td>Metrowerks CodeWarrior 9 through 9.5</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_34_1/libs/multi_index/doc/compiler_specifics.html#cw_9x">Boost 1.34.1</a></td>
|
||||
<td>July 2007</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Microsoft Visual C++ 6.0 Service Pack 5</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_36_0/libs/multi_index/doc/compiler_specifics.html#msvc_60">Boost 1.36</a></td>
|
||||
<td>August 2008</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td>Microsoft Visual C++ 7.0</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_35_0/libs/multi_index/doc/compiler_specifics.html#msvc_70">Boost 1.35</a></td>
|
||||
<td>March 2008</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Sun Studio 10 through 12 Update 1 for Solaris</td>
|
||||
<td><a href="http://www.boost.org/doc/libs/1_41_0/libs/multi_index/doc/compiler_specifics.html#sun_10">Boost 1.41</a></td>
|
||||
<td>November 2009</td>
|
||||
</tr>
|
||||
</table>
|
||||
</p>
|
||||
|
||||
<hr>
|
||||
|
||||
<div class="prev_link"><a href="reference/key_extraction.html"><img src="prev.gif" alt="key extraction" border="0"><br>
|
||||
Key extraction
|
||||
</a></div>
|
||||
<div class="up_link"><a href="index.html"><img src="up.gif" alt="index" border="0"><br>
|
||||
Index
|
||||
</a></div>
|
||||
<div class="next_link"><a href="performance.html"><img src="next.gif" alt="performance" border="0"><br>
|
||||
Performance
|
||||
</a></div><br clear="all" style="clear: all;">
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised August 20th 2014</p>
|
||||
|
||||
<p>© Copyright 2003-2014 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
http://www.boost.org/LICENSE_1_0.txt</a>)
|
||||
</p>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
+7
-7
@@ -105,7 +105,7 @@ See <a href="../example/bimap.cpp">source code</a>.
|
||||
This example shows how to construct a bidirectional map with
|
||||
<code>multi_index_container</code>. By a <i>bidirectional map</i> we mean
|
||||
a container of <code>(const FromType,const ToType)</code> pairs
|
||||
such that no two elements exist with the same first
|
||||
such that no two elements exists with the same first
|
||||
<i>or</i> second component (<code>std::map</code> only
|
||||
guarantees uniqueness of the first component). Fast lookup is provided
|
||||
for both keys. The program features a tiny Spanish-English
|
||||
@@ -174,9 +174,9 @@ involves having the manufactures stored in a separate
|
||||
|
||||
<span class=keyword>struct</span> <span class=identifier>car_model</span>
|
||||
<span class=special>{</span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>string</span> <span class=identifier>model</span><span class=special>;</span>
|
||||
<span class=keyword>const</span> <span class=identifier>car_manufacturer</span><span class=special>*</span> <span class=identifier>manufacturer</span><span class=special>;</span>
|
||||
<span class=keyword>int</span> <span class=identifier>price</span><span class=special>;</span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>string</span> <span class=identifier>model</span><span class=special>;</span>
|
||||
<span class=identifier>car_manufacturer</span><span class=special>*</span> <span class=identifier>manufacturer</span><span class=special>;</span>
|
||||
<span class=keyword>int</span> <span class=identifier>price</span><span class=special>;</span>
|
||||
<span class=special>};</span>
|
||||
</pre></blockquote>
|
||||
|
||||
@@ -222,7 +222,7 @@ of its associated <code>car_manufacturer</code> can be accomplished with
|
||||
<blockquote><pre>
|
||||
<span class=identifier>key_from_key</span><span class=special><</span>
|
||||
<span class=identifier>member</span><span class=special><</span><span class=identifier>car_manufacturer</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>string</span><span class=special>,&</span><span class=identifier>car_manufacturer</span><span class=special>::</span><span class=identifier>name</span><span class=special>>,</span>
|
||||
<span class=identifier>member</span><span class=special><</span><span class=identifier>car_model</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>car_manufacturer</span> <span class=special>*,&</span><span class=identifier>car_model</span><span class=special>::</span><span class=identifier>manufacturer</span><span class=special>></span>
|
||||
<span class=identifier>member</span><span class=special><</span><span class=identifier>car_model</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>car_manufacturer</span> <span class=special>*,</span><span class=identifier>car_model</span><span class=special>::</span><span class=identifier>manufacturer</span><span class=special>></span>
|
||||
<span class=special>></span>
|
||||
</pre></blockquote>
|
||||
|
||||
@@ -450,9 +450,9 @@ Tests
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised November 18th 2019</p>
|
||||
<p>Revised May 26th 2009</p>
|
||||
|
||||
<p>© Copyright 2003-2019 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2009 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+3
-2
@@ -67,6 +67,7 @@ examples of use developed in the documentation:
|
||||
<ul>
|
||||
<li><a href="tutorial/index.html">Tutorial</a></li>
|
||||
<li><a href="reference/index.html">Reference</a></li>
|
||||
<li><a href="compiler_specifics.html">Compiler specifics</a></li>
|
||||
<li><a href="performance.html">Performance</a></li>
|
||||
<li><a href="examples.html">Examples</a></li>
|
||||
<li><a href="tests.html">Tests</a></li>
|
||||
@@ -85,9 +86,9 @@ Tutorial
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised November 7th 2025</p>
|
||||
<p>Revised April 19th 2015</p>
|
||||
|
||||
<p>© Copyright 2003-2025 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2015 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+14
-14
@@ -6,7 +6,7 @@
|
||||
<title>Boost.MultiIndex Documentation - Performance</title>
|
||||
<link rel="stylesheet" href="style.css" type="text/css">
|
||||
<link rel="start" href="index.html">
|
||||
<link rel="prev" href="reference/key_extraction.html">
|
||||
<link rel="prev" href="compiler_specifics.html">
|
||||
<link rel="up" href="index.html">
|
||||
<link rel="next" href="examples.html">
|
||||
</head>
|
||||
@@ -15,8 +15,8 @@
|
||||
<h1><img src="../../../boost.png" alt="boost.png (6897 bytes)" align=
|
||||
"middle" width="277" height="86">Boost.MultiIndex Performance</h1>
|
||||
|
||||
<div class="prev_link"><a href="reference/key_extraction.html"><img src="prev.gif" alt="key extraction" border="0"><br>
|
||||
Key extraction
|
||||
<div class="prev_link"><a href="compiler_specifics.html"><img src="prev.gif" alt="compiler specifics" border="0"><br>
|
||||
Compiler specifics
|
||||
</a></div>
|
||||
<div class="up_link"><a href="index.html"><img src="up.gif" alt="index" border="0"><br>
|
||||
Index
|
||||
@@ -111,7 +111,7 @@ Consider the following instantiation of <code>multi_index_container</code>:
|
||||
<span class=keyword>int</span><span class=special>,</span>
|
||||
<span class=identifier>indexed_by</span><span class=special><</span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>>,</span>
|
||||
<span class=identifier>ordered_non_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>>,</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>greater</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>>,</span>
|
||||
<span class=identifier>ordered_non_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>>,</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>greater</span> <span class=special>>,</span>
|
||||
<span class=special>></span>
|
||||
<span class=special>></span> <span class=identifier>indexed_t</span><span class=special>;</span>
|
||||
</pre></blockquote>
|
||||
@@ -220,7 +220,7 @@ manual simulations.
|
||||
The gain in space consumption of <code>multi_index_container</code> with
|
||||
respect to its manual simulations is amenable to a very simple
|
||||
theoretical analysis. For simplicity, we will ignore alignment
|
||||
issues (which in general play in favor of <code>multi_index_container</code>).
|
||||
issues (which in general play in favor of <code>multi_index_container</code>.)
|
||||
</p>
|
||||
|
||||
<p>
|
||||
@@ -230,7 +230,7 @@ each index. Thus the node size is
|
||||
</p>
|
||||
|
||||
<blockquote>
|
||||
<i>S<sub>I</sub></i> = <i>e</i> + <i>h</i><sub>0</sub> + ··· +
|
||||
<i>S<sub>I</sub></i> = <i>e</i> + <i>h</i><sub>0</sub> + ··· +
|
||||
<i>h</i><sub><i>N</i>-1</sub>, where<br>
|
||||
<i>e</i> = size of the element,<br>
|
||||
<i>h</i><sub><i>i</i></sub> = size of the <i>i</i>-th header.
|
||||
@@ -247,7 +247,7 @@ the space allocated per element in a manual simulation is
|
||||
|
||||
<blockquote>
|
||||
<i>S<sub>M</sub></i> = (<i>e</i> + <i>h</i><sub>0</sub>) +
|
||||
(<i>p</i> + <i>h</i><sub>1</sub>) + ··· +
|
||||
(<i>p</i> + <i>h</i><sub>1</sub>) + ··· +
|
||||
(<i>p</i> + <i>h</i><sub><i>N</i>-1</sub>) =
|
||||
<i>S<sub>I</sub></i> + (<i>N</i>-1)<i>p</i>, where<br>
|
||||
<i>p</i> = size of a pointer.<br>
|
||||
@@ -285,7 +285,7 @@ Taking this fact into account, the former formula can be adjusted to:
|
||||
|
||||
<p>
|
||||
where <i>O</i> is the number of ordered indices of the container, and <i>w</i>
|
||||
is the system word size (typically 4 bytes on 32-bit architectures).
|
||||
is the system word size (typically 4 bytes on 32-bit architectures.)
|
||||
</p>
|
||||
|
||||
<p>
|
||||
@@ -473,7 +473,7 @@ sequenced index.</b>
|
||||
|
||||
<p>
|
||||
The figures confirm that in this case <code>multi_index_container</code> nodes are the
|
||||
same size as those of its <code>std::list</code> counterpart.
|
||||
same size than those of its <code>std::list</code> counterpart.
|
||||
</p>
|
||||
|
||||
<h4><a name="time_1s">Execution time</a></h4>
|
||||
@@ -725,7 +725,7 @@ factor, which ranges from 45% to 55%.
|
||||
We have shown that <code>multi_index_container</code> outperforms, both in space and
|
||||
time efficiency, equivalent data structures obtained from the manual
|
||||
combination of STL containers. This improvement gets larger when the number
|
||||
of indices increases.
|
||||
of indices increase.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
@@ -737,8 +737,8 @@ some improvements both in space consumption and execution time.
|
||||
|
||||
<hr>
|
||||
|
||||
<div class="prev_link"><a href="reference/key_extraction.html"><img src="prev.gif" alt="key extraction" border="0"><br>
|
||||
Key extraction
|
||||
<div class="prev_link"><a href="compiler_specifics.html"><img src="prev.gif" alt="compiler specifics" border="0"><br>
|
||||
Compiler specifics
|
||||
</a></div>
|
||||
<div class="up_link"><a href="index.html"><img src="up.gif" alt="index" border="0"><br>
|
||||
Index
|
||||
@@ -749,9 +749,9 @@ Examples
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised November 7th 2025</p>
|
||||
<p>Revised November 24th 2015</p>
|
||||
|
||||
<p>© Copyright 2003-2025 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2015 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+13
-241
@@ -199,13 +199,9 @@ together, with minor differences explicitly stated when they exist.
|
||||
<p>
|
||||
Except where noted or if the corresponding interface does not exist, hashed indices
|
||||
(both unique and non-unique) satisfy the C++ requirements for unordered associative
|
||||
containers at <b>[unord.req]</b> (supporting unique and equivalent keys, respectively).
|
||||
Iterators (including to the end of the index) and pointers and references to an element
|
||||
remain valid during the lifetime of the associated container (which can change
|
||||
upon swapping), or until the referred-to element is erased or extracted;
|
||||
pointers and references to an extracted element, but not so for iterators,
|
||||
become valid again once the element is re-inserted.
|
||||
Occasionally, the exception safety guarantees provided
|
||||
containers at <b>[unord.req]</b> (supporting unique and equivalent keys, respectively.)
|
||||
Validity of iterators and references to
|
||||
elements is preserved in all cases. Occasionally, the exception safety guarantees provided
|
||||
are actually stronger than required by the standard. We only provide descriptions of
|
||||
those types and operations that do not exactly conform to or are not mandated by the standard
|
||||
requirements.
|
||||
@@ -244,8 +240,6 @@ requirements.
|
||||
<span class=keyword>typedef</span> <b>implementation defined </b><span class=identifier>const_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>implementation defined </b><span class=identifier>local_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>implementation defined </b><span class=identifier>const_local_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>same as owning container </b><span class=identifier>node_type</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>following [container.insert.return] spec </b><span class=identifier>insert_return_type</span><span class=special>;</span>
|
||||
|
||||
<span class=comment>// construct/destroy/copy:</span>
|
||||
|
||||
@@ -286,11 +280,6 @@ requirements.
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>InputIterator</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>InputIterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>InputIterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>initializer_list</span><span class=special><</span><span class=identifier>value_type</span><span class=special>></span> <span class=identifier>list</span><span class=special>);</span>
|
||||
<span class=identifier>insert_return_type</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>node_type</span><span class=special>&&</span> <span class=identifier>nh</span><span class=special>);</span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>node_type</span><span class=special>&&</span> <span class=identifier>nh</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>node_type</span> <span class=identifier>extract</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
<span class=identifier>node_type</span> <span class=identifier>extract</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>key_type</span><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>iterator</span> <span class=identifier>erase</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
<span class=identifier>size_type</span> <span class=identifier>erase</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>key_type</span><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
@@ -308,16 +297,6 @@ requirements.
|
||||
<span class=keyword>void</span> <span class=identifier>clear</span><span class=special>()</span><span class=keyword>noexcept</span><span class=special>;</span>
|
||||
<span class=keyword>void</span> <span class=identifier>swap</span><span class=special>(</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span> <span class=keyword>void</span> <span class=identifier>merge</span><span class=special>(</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>pair</span><span class=special><</span><span class=identifier>iterator</span><span class=special>,</span><span class=keyword>bool</span><span class=special>></span> <span class=identifier>merge</span><span class=special>(</span>
|
||||
<span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>i</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>merge</span><span class=special>(</span>
|
||||
<span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>first</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
|
||||
<span class=comment>// observers:</span>
|
||||
|
||||
<span class=identifier>key_from_value</span> <span class=identifier>key_extractor</span><span class=special>()</span><span class=keyword>const</span><span class=special>;</span>
|
||||
@@ -344,15 +323,6 @@ requirements.
|
||||
<span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>const</span> <span class=identifier>CompatibleHash</span><span class=special>&</span> <span class=identifier>hash</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>CompatiblePred</span><span class=special>&</span> <span class=identifier>eq</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>></span>
|
||||
<span class=keyword>bool</span> <span class=identifier>contains</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
<span class=keyword>template</span><span class=special><</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>CompatibleHash</span><span class=special>,</span> <span class=keyword>typename</span> <span class=identifier>CompatiblePred</span>
|
||||
<span class=special>></span>
|
||||
<span class=keyword>bool</span> <span class=identifier>contains</span><span class=special>(</span>
|
||||
<span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>const</span> <span class=identifier>CompatibleHash</span><span class=special>&</span> <span class=identifier>hash</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>CompatiblePred</span><span class=special>&</span> <span class=identifier>eq</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>></span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>pair</span><span class=special><</span><span class=identifier>iterator</span><span class=special>,</span><span class=identifier>iterator</span><span class=special>></span> <span class=identifier>equal_range</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
<span class=keyword>template</span><span class=special><</span>
|
||||
@@ -458,7 +428,7 @@ following types:
|
||||
which determines the mechanism for extracting a key from <code>Value</code>,
|
||||
must be a model of <a href="key_extraction.html#key_extractors">
|
||||
<code>Key Extractor</code></a> from <code>Value</code>. <code>Hash</code> is a
|
||||
<code>CopyConstructible</code> unary function object
|
||||
<code>CopyConstructible</code>unary function object
|
||||
taking a single argument of type <code>KeyFromValue::result_type</code> and returning a
|
||||
value of type <code>std::size_t</code> in the range
|
||||
<code>[0, std::numeric_limits<std::size_t>::max())</code>.
|
||||
@@ -484,10 +454,7 @@ local_iterator<br>
|
||||
const_local_iterator</code>
|
||||
|
||||
<blockquote>
|
||||
These types are forward iterators. They depend only on <code>node_type</code>,
|
||||
the position of the index in the <code>multi_index_container</code>, and whether
|
||||
the index is unique or not (this implies that, for instance, iterators to elements transferred
|
||||
from a unique index to a non-unique one will become invalid).
|
||||
These types are forward iterators.
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="constructors">Constructors, copy and assignment</a></h4>
|
||||
@@ -676,86 +643,6 @@ to which this index belongs if
|
||||
</pre></blockquote>
|
||||
</blockquote>
|
||||
|
||||
<code>insert_return_type insert(node_type&& nh);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>nh.empty() || get_allocator()==nh.get_allocator()</code>.<br>
|
||||
<b>Effects:</b> Does nothing if <code>nh</code> is empty; otherwise,
|
||||
inserts the node owned by <code>nh</code> into the
|
||||
<code>multi_index_container</code> to which the index belongs if
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists with
|
||||
equivalent key,</li>
|
||||
<li>AND insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
</ul>
|
||||
<b>Postconditions:</b> <code>nh</code> is empty.<br>
|
||||
<b>Returns:</b> A value <code>p</code> of type <code>insert_return_type</code>.
|
||||
If <code>nh</code> is empty, <code>p.position</code> is <code>end()</code>,
|
||||
<code>p.inserted</code> is <code>false</code> and <code>p.node</code> is empty;
|
||||
on successful insertion, <code>p.position</code> points to the element inserted,
|
||||
<code>p.inserted</code> is <code>true</code> and <code>p.node</code>
|
||||
is empty;
|
||||
if the insertion failed, <code>p.position</code> points to an element that caused
|
||||
the insertion to be banned, <code>p.inserted</code> is <code>false</code> and
|
||||
<code>p.node</code> owns the original node.
|
||||
Note that more than one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> <code>O(I(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong, except that rehashing may occur even if the
|
||||
operation fails. If an exception is thrown, <code>nh</code> is not changed.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>iterator insert(const_iterator position,node_type&& nh);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>nh.empty() || get_allocator()==nh.get_allocator()</code>.
|
||||
<code>position</code> is a valid iterator of the index.<br>
|
||||
<b>Effects:</b> Does nothing if <code>nh</code> is empty; otherwise,
|
||||
inserts the node owned by <code>nh</code> into the
|
||||
<code>multi_index_container</code> to which the index belongs if
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists with
|
||||
equivalent key,</li>
|
||||
<li>AND insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
</ul>
|
||||
<code>position</code> is used as a hint to improve the efficiency of the
|
||||
operation.<br>
|
||||
<b>Postconditions:</b> <code>nh</code> is empty if insertion succeeds,
|
||||
and is not changed otherwise.<br>
|
||||
<b>Returns:</b> <code>end()</code> if <code>nh</code> is empty.
|
||||
On successful insertion, an iterator to the newly inserted
|
||||
element; otherwise, an iterator to an element that caused the insertion to be
|
||||
banned. Note that more than one element can be causing insertion not to be
|
||||
allowed.<br>
|
||||
<b>Complexity:</b> <code>O(H(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong, except that rehashing may occur even if the
|
||||
operation fails.
|
||||
If an exception is thrown, <code>nh</code> is not changed.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>node_type extract(const_iterator position);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>position</code> is a valid dereferenceable iterator
|
||||
of the index.<br>
|
||||
<b>Effects:</b> Extracts the node of the element pointed to by <code>position</code>.<br>
|
||||
<b>Returns:</b> A node handle owning the extracted node.<br>
|
||||
<b>Complexity:</b> <code>O(D(n))</code>.<br>
|
||||
<b>Exception safety:</b> <code>nothrow</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>node_type extract(const key_type& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Effects:</b> Extracts the node of the first element
|
||||
with key equivalent to <code>x</code>, if there is any.<br>
|
||||
<b>Returns:</b> A node handle owning the extracted node, or empty otherwise.<br>
|
||||
<b>Complexity:</b> Average case <code>O(1 + D(n))</code>, worst case
|
||||
<code>O(n<sub>dist</sub> + D(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>iterator erase(iterator position);</code>
|
||||
|
||||
<blockquote>
|
||||
@@ -774,7 +661,7 @@ if no such element exists.<br>
|
||||
<blockquote>
|
||||
<b>Effects:</b> Deletes the elements with key equivalent to <code>x</code>.<br>
|
||||
<b>Returns:</b> Number of elements deleted.<br>
|
||||
<b>Complexity:</b> Average case <code>O(1 + m*D(n))</code>, worst case
|
||||
<b>Complexity:</b> Average case, <code>O(1 + m*D(n))</code>, worst case
|
||||
<code>O(n<sub>dist</sub> + m*D(n))</code>, where <code>m</code> is
|
||||
the number of elements deleted.<br>
|
||||
<b>Exception safety:</b> Basic.<br>
|
||||
@@ -802,7 +689,7 @@ the number of elements in [<code>first</code>,<code>last</code>).<br>
|
||||
<code>position</code> is a valid dereferenceable iterator of the index.<br>
|
||||
<b>Effects:</b> Assigns the value <code>x</code> to the element pointed
|
||||
to by <code>position</code> into the <code>multi_index_container</code> to which
|
||||
the index belongs if, for the value <code>x</code>,
|
||||
the index belongs if, for the value <code>x</code>
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists
|
||||
(except possibly <code>*position</code>) with equivalent key,</li>
|
||||
@@ -938,89 +825,6 @@ with <code>mod'</code> and <code>back</code> defined in such a way that
|
||||
<code>key</code> is the internal <code>KeyFromValue</code> object of the index.
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename Index> void merge(Index&& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>. <code>get_allocator()==x.get_allocator()</code>.<br>
|
||||
<b>Effects:</b>
|
||||
<blockquote><pre>
|
||||
<span class=identifier>merge</span><span class=special>(</span><span class=identifier>x</span><span class=special>,</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>begin</span><span class=special>(),</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>end</span><span class=special>());</span>
|
||||
</pre></blockquote>
|
||||
</blockquote>
|
||||
|
||||
<code>
|
||||
template<typename Index> std::pair<iterator,bool> merge(<br>
|
||||
Index&& x,typename std::remove_reference_t<Index>::const_iterator i);
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>. <code>get_allocator()==x.get_allocator()</code>.
|
||||
<code>i</code> is a valid dereferenceable iterator of <code>x</code>.<br>
|
||||
<b>Effects:</b> Does nothing if the source and destination containers are the same;
|
||||
otherwise, transfers the node of the element referred to by <code>i</code> into the
|
||||
<code>multi_index_container</code> to which the destination index belongs if
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists with
|
||||
equivalent key,</li>
|
||||
<li>AND insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
</ul>
|
||||
Note that no element is copied or destroyed in the process.<br>
|
||||
<b>Postconditions:</b> If transfer succeeds, for any index in the source container
|
||||
having the same <code>iterator</code>/<code>const_iterator</code> types as the corresponding
|
||||
index in the destination container, iterators referring to <code>*i</code>
|
||||
remain valid and behave as iterators of the destination index.<br>
|
||||
<b>Returns:</b> The return value is a pair <code>p</code>. <code>p.second</code>
|
||||
is <code>true</code> if and only if transfer took place or the source and destination
|
||||
containers are the same. If <code>p.second</code> is <code>true</code>,
|
||||
<code>p.first</code> points to <code>*i</code>; otherwise, <code>p.first</code>
|
||||
points to an element that caused the insertion to be banned. Note that more than
|
||||
one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> If the source and destination containers are the same,
|
||||
constant; otherwise, <code>O(I(n)+D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> If the source and destination containers are the same,
|
||||
<code>nothrow</code>; otherwise strong.
|
||||
</blockquote>
|
||||
|
||||
<code>
|
||||
template<typename Index> void merge(<br>
|
||||
Index&& x,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator first,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator last);
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>. <code>get_allocator()==x.get_allocator()</code>.
|
||||
[<code>first</code>,<code>last</code>) is a valid range of <code>x</code>.<br>
|
||||
<b>Effects:</b> Does nothing if the source and destination containers are the same;
|
||||
otherwise, for each node in [<code>first</code>,<code>last</code>), in this order,
|
||||
the node is transferred to the <code>multi_index_container</code> to which the
|
||||
destination index belongs if
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists with
|
||||
equivalent key,</li>
|
||||
<li>AND insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
</ul>
|
||||
Note that no element is copied or destroyed in the process.<br>
|
||||
<b>Postconditions:</b> For any index in the source container having the same
|
||||
<code>iterator</code>/<code>const_iterator</code> types as the corresponding
|
||||
index in the destination container, iterators referring to the transferred elements
|
||||
remain valid and behave as iterators of the destination index.<br>
|
||||
<b>Complexity:</b> If the source and destination containers are the same,
|
||||
constant; otherwise, <code>O(m*(I(n+m)+D(x.size())))</code>, where
|
||||
<code>m</code> is the number of elements in [<code>first</code>,
|
||||
<code>last</code>).<br>
|
||||
<b>Exception safety:</b> If the source and destination containers are the same,
|
||||
<code>nothrow</code>; otherwise basic.
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="observers">Observers</a></h4>
|
||||
|
||||
<p>Apart from standard <code>hash_function</code> and <code>key_eq</code>,
|
||||
@@ -1154,35 +958,6 @@ size_type count(<br>
|
||||
<code>O(count(x,hash,eq)+n<sub>dist</sub>)</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename CompatibleKey><br>
|
||||
bool contains(const CompatibleKey& x)const;
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>CompatibleKey</code> is a compatible key of
|
||||
(<code>hasher</code>, <code>key_equal</code>).<br>
|
||||
<b>Effects:</b> Returns <code>true</code> iff there is some element with key equivalent to <code>x</code>.<br>
|
||||
<b>Complexity:</b> Average case <code>O(1)</code> (constant), worst case
|
||||
<code>O(n<sub>dist</sub>)</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>template<<br>
|
||||
typename CompatibleKey,typename CompatibleHash, typename CompatiblePred<br>
|
||||
><br>
|
||||
bool contains(<br>
|
||||
const CompatibleKey& x,<br>
|
||||
const CompatibleHash& hash,const CompatiblePred& eq)const;
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> (<code>CompatibleKey</code>, <code>CompatibleHash</code>,
|
||||
<code>CompatiblePred</code>) is a compatible extension of
|
||||
(<code>hasher</code>, <code>key_equal</code>).<br>
|
||||
<b>Effects:</b> Returns <code>true</code> iff there is some element with key equivalent to <code>x</code>.<br>
|
||||
<b>Complexity:</b> Average case <code>O(1)</code> (constant), worst case
|
||||
<code>O(n<sub>dist</sub>)</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename CompatibleKey><br>
|
||||
std::pair<iterator,iterator> equal_range(const CompatibleKey& x)const;
|
||||
</code>
|
||||
@@ -1305,12 +1080,9 @@ Operation: loading of a <code>multi_index_container</code> <code>m'</code> from
|
||||
input archive (XML archive) <code>ar</code>.
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> Additionally to the general requirements, the binary predicate
|
||||
<code><i>value_eq</i>(m'.get<i>())</code> must be serialization-compatible with
|
||||
<code><i>value_eq</i>(m.get<i>())</code>, where
|
||||
<code><i>value_eq</i>(c)(x,y)</code> is defined as
|
||||
<code>c.key_eq()(c.key_extractor()(x),c.key_extractor()(y))</code>
|
||||
and <code>i</code> is the position of the hashed index in the container.<br>
|
||||
<b>Requires:</b> Additionally to the general requirements, <code>key_eq()</code>
|
||||
must be serialization-compatible with <code>m.get<i>().key_eq()</code>,
|
||||
where <code>i</code> is the position of the hashed index in the container.<br>
|
||||
<b>Postconditions:</b> On successful loading, the range
|
||||
[<code>begin()</code>, <code>end()</code>) contains restored copies of every
|
||||
element in [<code>m.get<i>().begin()</code>, <code>m.get<i>().end()</code>),
|
||||
@@ -1355,7 +1127,7 @@ then <code>*it'</code> is the restored copy of <code>*it</code>; if <code>it</co
|
||||
was <code>m.get<i>().end(n)</code> for some <code>n</code>, then
|
||||
<code>it'==m'.get<i>().end(n)</code> (where <code>m</code> is the original
|
||||
<code>multi_index_container</code>, <code>m'</code> its restored copy
|
||||
and <code>i</code> is the ordinal of the index).<br>
|
||||
and <code>i</code> is the ordinal of the index.)<br>
|
||||
<b>Note:</b> It is allowed that <code>it</code> be a <code>const_local_iterator</code>
|
||||
and the restored <code>it'</code> a <code>local_iterator</code>, or vice versa.
|
||||
</blockquote>
|
||||
@@ -1374,9 +1146,9 @@ Sequenced indices
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised March 15th 2024</p>
|
||||
<p>Revised August 25th 2017</p>
|
||||
|
||||
<p>© Copyright 2003-2024 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2017 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+39
-22
@@ -81,7 +81,7 @@ appropriate interface of some index of the <code>multi_index_container</code>;
|
||||
these operations, however, do have an impact on all other indices as
|
||||
well: for instance, insertion through a given index may fail because
|
||||
there exists another index which bans the operation in order to preserve
|
||||
its invariant (like uniqueness of elements). This circumstance, rather
|
||||
its invariant (like uniqueness of elements.) This circumstance, rather
|
||||
than being an obstacle, yields much of the power of Boost.MultiIndex:
|
||||
equivalent constructions based on manual composition of standard
|
||||
containers would have to add a fair amount of code in order to
|
||||
@@ -103,7 +103,7 @@ six primitives:
|
||||
</ul>
|
||||
The last two primitives deserve some further explanation: in order to
|
||||
guarantee the invariants associated to each index (e.g. some definite
|
||||
ordering), elements of a <code>multi_index_container</code> are not mutable.
|
||||
ordering,) elements of a <code>multi_index_container</code> are not mutable.
|
||||
To overcome this restriction, indices expose member functions
|
||||
for replacement and modification which allow for the mutation of elements
|
||||
in a controlled fashion. Immutability of elements does not significantly
|
||||
@@ -120,8 +120,8 @@ These global operations are not directly exposed to the user, but rather
|
||||
they are wrapped as appropriate by each index (for instance, ordered indices
|
||||
provide a set-like suite of insertion member functions, whereas sequenced
|
||||
and random access indices have <code>push_back</code> and <code>push_front</code>
|
||||
operations). Boost.MultiIndex poses no particular conditions on
|
||||
the interface of indices, although each index provided satisfies the C++ requirements for
|
||||
operations.) Boost.MultiIndex poses no particular conditions on
|
||||
the interface of indices, although each index provided satisfy the C++ requirements for
|
||||
standard containers to the maximum extent possible within the conceptual framework
|
||||
of the library.
|
||||
</p>
|
||||
@@ -156,16 +156,16 @@ with <code>N</code> indices labelled <code>0</code>,...,<code>N-1</code>
|
||||
whose complexity signatures are
|
||||
(<code>c<sub>i</sub></code>,<code>i<sub>i</sub></code>,<code>h<sub>i</sub></code>,<code>d<sub>i</sub></code>,<code>r<sub>i</sub></code>,<code>m<sub>i</sub></code>);
|
||||
the insertion of an element in such a container is then of complexity
|
||||
<code>O(i<sub>0</sub>(n)+···+i<sub>N-1</sub>(n))</code> where <code>n</code>
|
||||
<code>O(i<sub>0</sub>(n)+···+i<sub>N-1</sub>(n))</code> where <code>n</code>
|
||||
is the number of elements. To abbreviate notation, we adopt the
|
||||
following definitions:
|
||||
<ul>
|
||||
<li><code>C(n)=c<sub>0</sub>(n)+···+c<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>I(n)=i<sub>0</sub>(n)+···+i<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>H(n)=h<sub>0</sub>(n)+···+h<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>D(n)=d<sub>0</sub>(n)+···+d<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>R(n)=r<sub>0</sub>(n)+···+r<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>M(n)=m<sub>0</sub>(n)+···+m<sub>N-1</sub>(n)</code>.</li>
|
||||
<li><code>C(n)=c<sub>0</sub>(n)+···+c<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>I(n)=i<sub>0</sub>(n)+···+i<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>H(n)=h<sub>0</sub>(n)+···+h<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>D(n)=d<sub>0</sub>(n)+···+d<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>R(n)=r<sub>0</sub>(n)+···+r<sub>N-1</sub>(n)</code>,</li>
|
||||
<li><code>M(n)=m<sub>0</sub>(n)+···+m<sub>N-1</sub>(n)</code>.</li>
|
||||
</ul>
|
||||
For instance, consider a <code>multi_index_container</code> with two ordered indices,
|
||||
for which <code>i(n)=log(n)</code>, and a sequenced index with <code>i(n)=1</code>
|
||||
@@ -212,7 +212,7 @@ index specifiers
|
||||
|
||||
<span class=keyword>namespace</span> <span class=identifier>multi_index</span><span class=special>{</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>T</span><span class=special>,</span><span class=keyword>typename</span><span class=special>...</span> <span class=identifier>Ts</span><span class=special>></span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>T0</span><span class=special>,...,</span><span class=keyword>typename</span> <span class=identifier>Tn</span><span class=special>></span>
|
||||
<span class=keyword>struct</span> <span class=identifier>indexed_by</span><span class=special>;</span>
|
||||
|
||||
<span class=special>}</span> <span class=comment>// namespace boost::multi_index</span>
|
||||
@@ -223,19 +223,24 @@ index specifiers
|
||||
<h3><a name="indexed_by">Class template <code>indexed_by</code></a></h3>
|
||||
|
||||
<p>
|
||||
<code>indexed_by</code> is meant to be used to specify a
|
||||
<code>indexed_by</code> is a model of
|
||||
<a href="../../../../libs/mpl/doc/refmanual/random-access-sequence.html">
|
||||
<code>MPL Random Access Sequence</code></a> and
|
||||
<a href="../../../../libs/mpl/doc/refmanual/extensible-sequence.html">
|
||||
<code>MPL Extensible Sequence</code></a> meant to be used to specify a
|
||||
compile-time list of indices as the <code>IndexSpecifierList</code> of
|
||||
<code>multi_index_container</code>.
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>T</span><span class=special>,</span><span class=keyword>typename</span><span class=special>...</span> <span class=identifier>Ts</span><span class=special>></span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>T0</span><span class=special>,...,</span><span class=keyword>typename</span> <span class=identifier>Tn</span><span class=special>></span>
|
||||
<span class=keyword>struct</span> <span class=identifier>indexed_by</span><span class=special>;</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
Each user-provided element of <code>indexed_list</code> must be an index
|
||||
specifier. At least an element must be provided.
|
||||
specifier. At least an element must be provided. The maximum number of elements
|
||||
of an <code>indexed_by</code> sequence is implementation defined.
|
||||
</p>
|
||||
|
||||
<h2><a name="tags">Tags</a></h2>
|
||||
@@ -259,7 +264,7 @@ class template <a href="#tag"><code>tag</code></a>.
|
||||
|
||||
<span class=keyword>namespace</span> <span class=identifier>multi_index</span><span class=special>{</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span><span class=special>...</span> <span class=identifier>Ts</span><span class=special>></span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>T0</span><span class=special>,...,</span><span class=keyword>typename</span> <span class=identifier>Tn</span><span class=special>></span>
|
||||
<span class=keyword>struct</span> <span class=identifier>tag</span><span class=special>;</span>
|
||||
|
||||
<span class=special>}</span> <span class=comment>// namespace boost::multi_index</span>
|
||||
@@ -275,13 +280,25 @@ sequence of tags to be assigned to an index in instantiation time.
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span><span class=special>...</span> <span class=identifier>Ts</span><span class=special>></span>
|
||||
<span class=keyword>struct</span> <span class=identifier>tag</span><span class=special>;</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>T0</span><span class=special>,...,</span><span class=keyword>typename</span> <span class=identifier>Tn</span><span class=special>></span>
|
||||
<span class=keyword>struct</span> <span class=identifier>tag</span>
|
||||
<span class=special>{</span>
|
||||
<span class=keyword>typedef</span> <b>implementation defined</b> <span class=identifier>type</span><span class=special>;</span>
|
||||
<span class=special>};</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
Elements of <code>tag</code> can be any type, though the user is expected
|
||||
to provide classes with mnemonic names. Duplicate elements are not allowed.
|
||||
The maximum number of elements of a <code>tag</code> instantiation is
|
||||
implementation defined.
|
||||
The nested
|
||||
<code>type</code> is a model of
|
||||
<a href="../../../../libs/mpl/doc/refmanual/random-access-sequence.html">
|
||||
<code>MPL Random Access Sequence</code></a> and
|
||||
<a href="../../../../libs/mpl/doc/refmanual/extensible-sequence.html">
|
||||
<code>MPL Extensible Sequence</code></a> containing the types <code>T0</code>, ... ,
|
||||
<code>Tn</code> in the same order as specified.
|
||||
</p>
|
||||
|
||||
<h2><a name="index_catalog">Indices provided by Boost.MultiIndex</a></h2>
|
||||
@@ -295,7 +312,7 @@ elements, as described in the <a href="key_extraction.html">key extraction
|
||||
reference</a>.
|
||||
<ul>
|
||||
<li><a href="ord_indices.html">Ordered indices</a> sort the elements
|
||||
on the key and provide fast lookup capabilities.</li>
|
||||
on the key and provide fast lookup capabilites.</li>
|
||||
<li><a href="rnk_indices.html">Ranked indices</a> are a variation of
|
||||
ordered indices providing extra operations based on
|
||||
<i>rank</i>, the numerical position of an element
|
||||
@@ -319,7 +336,7 @@ reference</a>.
|
||||
<h2><a name="views">Index views</a></h2>
|
||||
|
||||
<p>
|
||||
The following concept is used by the rearrange facilities of non-key-based
|
||||
The following concept is used by the rearrange facilities of non key-based
|
||||
indices. Given an index <code>i</code> of type <code>Index</code>, a <i>view
|
||||
of <code>i</code></i> is any range [<code>first</code>,<code>last</code>)
|
||||
where <code>first</code> and <code>last</code> are input iterators such that
|
||||
@@ -369,9 +386,9 @@ Ordered indices
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised October 25th 2025</p>
|
||||
<p>Revised April 19th 2015</p>
|
||||
|
||||
<p>© Copyright 2003-2025 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2015 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+214
-230
File diff suppressed because it is too large
Load Diff
@@ -235,15 +235,16 @@ and for access to the indices held.
|
||||
<p>
|
||||
A <code>multi_index_container</code> type is instantiated with the type of the
|
||||
elements contained and a non-empty
|
||||
<a href="../../../../libs/mp11/doc/html/mp11.html#definitions">Mp11 list</a>
|
||||
specifying which indices conform the class.
|
||||
<a href="../../../../libs/mpl/doc/refmanual/forward-sequence.html">
|
||||
<code>MPL Forward Sequence</code></a> specifying which indices conform the
|
||||
class.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
For convenience of use, all public methods and types of the first index
|
||||
specified are inherited by <code>multi_index_container</code>. This also includes global
|
||||
operators and functions associated with the index (vg. comparison and
|
||||
<code>swap</code>).
|
||||
<code>swap</code>.)
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
@@ -263,7 +264,6 @@ operators and functions associated with the index (vg. comparison and
|
||||
<span class=keyword>typedef</span> <b>implementation defined</b> <span class=identifier>iterator_type_list</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>implementation defined</b> <span class=identifier>const_iterator_type_list</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <span class=identifier>Allocator</span> <span class=identifier>allocator_type</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>implementation defined</b> <span class=identifier>node_type</span><span class=special>;</span>
|
||||
|
||||
<span class=comment>// nested class templates:</span>
|
||||
|
||||
@@ -305,12 +305,6 @@ operators and functions associated with the index (vg. comparison and
|
||||
<span class=keyword>const</span> <span class=identifier>multi_index_container</span><span class=special><</span><span class=identifier>Value</span><span class=special>,</span><span class=identifier>IndexSpecifierList</span><span class=special>,</span><span class=identifier>Allocator</span><span class=special>>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=identifier>multi_index_container</span><span class=special>(</span>
|
||||
<span class=identifier>multi_index_container</span><span class=special><</span><span class=identifier>Value</span><span class=special>,</span><span class=identifier>IndexSpecifierList</span><span class=special>,</span><span class=identifier>Allocator</span><span class=special>>&&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=identifier>multi_index_container</span><span class=special>(</span>
|
||||
<span class=keyword>const</span> <span class=identifier>multi_index_container</span><span class=special><</span><span class=identifier>Value</span><span class=special>,</span><span class=identifier>IndexSpecifierList</span><span class=special>,</span><span class=identifier>Allocator</span><span class=special>>&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>const</span> <span class=identifier>allocator_type</span><span class=special>&</span> <span class=identifier>al</span><span class=special>);</span>
|
||||
<span class=identifier>multi_index_container</span><span class=special>(</span>
|
||||
<span class=identifier>multi_index_container</span><span class=special><</span><span class=identifier>Value</span><span class=special>,</span><span class=identifier>IndexSpecifierList</span><span class=special>,</span><span class=identifier>Allocator</span><span class=special>>&&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>const</span> <span class=identifier>allocator_type</span><span class=special>&</span> <span class=identifier>al</span><span class=special>);</span>
|
||||
|
||||
<span class=special>~</span><span class=identifier>multi_index_container</span><span class=special>();</span>
|
||||
|
||||
@@ -388,7 +382,7 @@ operators and functions associated with the index (vg. comparison and
|
||||
<span class=special>>::</span><span class=identifier>type</span><span class=special>&</span>
|
||||
<span class=identifier>get</span><span class=special>(</span><span class=identifier>multi_index_container</span><span class=special><</span><span class=identifier>Value</span><span class=special>,</span><span class=identifier>IndexSpecifierList</span><span class=special>,</span><span class=identifier>Allocator</span><span class=special>>&</span> <span class=identifier>m</span><span class=special>)</span><span class=keyword>noexcept</span>
|
||||
<span class=special>{</span>
|
||||
<span class=keyword>return</span> <span class=identifier>m</span><span class=special>.</span><span class=keyword>template</span> <span class=identifier>get</span><span class=special><</span><span class=identifier>N</span><span class=special>>();</span>
|
||||
<span class=keyword>return</span> <span class=identifier>m</span><span class=special>.</span><span class=identifier>get</span><span class=special><</span><span class=identifier>N</span><span class=special>>();</span>
|
||||
<span class=special>}</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span>
|
||||
@@ -399,7 +393,7 @@ operators and functions associated with the index (vg. comparison and
|
||||
<span class=special>>::</span><span class=identifier>type</span><span class=special>&</span>
|
||||
<span class=identifier>get</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>multi_index_container</span><span class=special><</span><span class=identifier>Value</span><span class=special>,</span><span class=identifier>IndexSpecifierList</span><span class=special>,</span><span class=identifier>Allocator</span><span class=special>>&</span> <span class=identifier>m</span><span class=special>)</span><span class=keyword>noexcept</span>
|
||||
<span class=special>{</span>
|
||||
<span class=keyword>return</span> <span class=identifier>m</span><span class=special>.</span><span class=keyword>template</span> <span class=identifier>get</span><span class=special><</span><span class=identifier>N</span><span class=special>>();</span>
|
||||
<span class=keyword>return</span> <span class=identifier>m</span><span class=special>.</span><span class=identifier>get</span><span class=special><</span><span class=identifier>N</span><span class=special>>();</span>
|
||||
<span class=special>}</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span>
|
||||
@@ -410,7 +404,7 @@ operators and functions associated with the index (vg. comparison and
|
||||
<span class=special>>::</span><span class=identifier>type</span><span class=special>&</span>
|
||||
<span class=identifier>get</span><span class=special>(</span><span class=identifier>multi_index_container</span><span class=special><</span><span class=identifier>Value</span><span class=special>,</span><span class=identifier>IndexSpecifierList</span><span class=special>,</span><span class=identifier>Allocator</span><span class=special>>&</span> <span class=identifier>m</span><span class=special>)</span><span class=keyword>noexcept</span>
|
||||
<span class=special>{</span>
|
||||
<span class=keyword>return</span> <span class=identifier>m</span><span class=special>.</span><span class=keyword>template</span> <span class=identifier>get</span><span class=special><</span><span class=identifier>Tag</span><span class=special>>();</span>
|
||||
<span class=keyword>return</span> <span class=identifier>m</span><span class=special>.</span><span class=identifier>get</span><span class=special><</span><span class=identifier>Tag</span><span class=special>>();</span>
|
||||
<span class=special>}</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span>
|
||||
@@ -421,7 +415,7 @@ operators and functions associated with the index (vg. comparison and
|
||||
<span class=special>>::</span><span class=identifier>type</span><span class=special>&</span>
|
||||
<span class=identifier>get</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>multi_index_container</span><span class=special><</span><span class=identifier>Value</span><span class=special>,</span><span class=identifier>IndexSpecifierList</span><span class=special>,</span><span class=identifier>Allocator</span><span class=special>>&</span> <span class=identifier>m</span><span class=special>)</span><span class=keyword>noexcept</span>
|
||||
<span class=special>{</span>
|
||||
<span class=keyword>return</span> <span class=identifier>m</span><span class=special>.</span><span class=keyword>template</span> <span class=identifier>get</span><span class=special><</span><span class=identifier>Tag</span><span class=special>>();</span>
|
||||
<span class=keyword>return</span> <span class=identifier>m</span><span class=special>.</span><span class=identifier>get</span><span class=special><</span><span class=identifier>Tag</span><span class=special>>();</span>
|
||||
<span class=special>}</span>
|
||||
|
||||
<span class=comment>// multi_index_container global functions for projection of iterators:</span>
|
||||
@@ -530,10 +524,13 @@ scheme outlined in the
|
||||
</li>
|
||||
<li><code>IndexSpecifierList</code> specifies the indices that the
|
||||
<code>multi_index_container</code> is composed of. It must be a non-empty
|
||||
<a href="../../../../libs/mp11/doc/html/mp11.html#definitions">Mp11 list</a>
|
||||
of index specifiers. For syntactic convenience, the
|
||||
<a href="../../../../libs/mpl/doc/refmanual/forward-sequence.html">
|
||||
<code>MPL Forward Sequence</code></a> (and, preferrably,
|
||||
an <a href="../../../../libs/mpl/doc/refmanual/random-access-sequence.html">
|
||||
<code>MPL Random Access Sequence</code></a>) of index specifiers. For
|
||||
syntactic convenience, the
|
||||
<a href="indices.html#indexed_by"><code>indexed_by</code></a>
|
||||
construct can be used.
|
||||
MPL sequence can be used.
|
||||
</li>
|
||||
<li><code>Allocator</code> must be an allocator of <code>Value</code> objects
|
||||
satisfying the associated C++ requirements at <b>[allocator.requirements]</b>.
|
||||
@@ -552,21 +549,13 @@ scheme outlined in the
|
||||
<code>p</code> shall dereference to <code>*p</code>.
|
||||
</li>
|
||||
</ul>
|
||||
<code>multi_index_container</code>s and all their iterators do not store references
|
||||
to allocated elements other than through the allocator's pointer type.
|
||||
</li>
|
||||
</ol>
|
||||
|
||||
Indices of a given <code>multi_index_container</code> instantiation cannot have
|
||||
duplicate <a href="indices.html#tags">tags</a>, either within a single
|
||||
index or in two different indices.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
In what follows, the number of indices of the <code>multi_index_container</code>
|
||||
is named <code>I</code>.
|
||||
</p>
|
||||
|
||||
<h4><a name="types">Nested types</a></h4>
|
||||
|
||||
<code>ctor_args_list</code>
|
||||
@@ -597,16 +586,22 @@ Same type as <code>IndexSpecifierList</code>.
|
||||
<code>index_type_list</code>
|
||||
|
||||
<blockquote>
|
||||
<a href="../../../../libs/mp11/doc/html/mp11.html#definitions">Mp11 list</a>
|
||||
containing the types of the indices held by
|
||||
Model of
|
||||
<a href="../../../../libs/mpl/doc/refmanual/random-access-sequence.html">
|
||||
<code>MPL Random Access Sequence</code></a> and
|
||||
<a href="../../../../libs/mpl/doc/refmanual/extensible-sequence.html">
|
||||
<code>MPL Extensible Sequence</code></a> containing the types of the indices held by
|
||||
the <code>multi_index_container</code>, in the same order as they were specified.
|
||||
</blockquote>
|
||||
|
||||
<code>iterator_type_list</code>
|
||||
|
||||
<blockquote>
|
||||
<a href="../../../../libs/mp11/doc/html/mp11.html#definitions">Mp11 list</a>
|
||||
containing the types of the iterators of
|
||||
Model of
|
||||
<a href="../../../../libs/mpl/doc/refmanual/random-access-sequence.html">
|
||||
<code>MPL Random Access Sequence</code></a> and
|
||||
<a href="../../../../libs/mpl/doc/refmanual/extensible-sequence.html">
|
||||
<code>MPL Extensible Sequence</code></a> containing the types of the iterators of
|
||||
the indices held by the <code>multi_index_container</code>, in the same order as they were
|
||||
specified.
|
||||
</blockquote>
|
||||
@@ -614,28 +609,15 @@ specified.
|
||||
<code>const_iterator_type_list</code>
|
||||
|
||||
<blockquote>
|
||||
<a href="../../../../libs/mp11/doc/html/mp11.html#definitions">Mp11 list</a>
|
||||
containing the types of the constant
|
||||
Model of
|
||||
<a href="../../../../libs/mpl/doc/refmanual/random-access-sequence.html">
|
||||
<code>MPL Random Access Sequence</code></a> and
|
||||
<a href="../../../../libs/mpl/doc/refmanual/extensible-sequence.html">
|
||||
<code>MPL Extensible Sequence</code></a> containing the types of the constant
|
||||
iterators of the indices held by the <code>multi_index_container</code>, in the same order
|
||||
as they were specified.
|
||||
</blockquote>
|
||||
|
||||
<a name="node_type"><code>node_type</code></a>
|
||||
|
||||
<blockquote>
|
||||
Node handle class following the standard specification at
|
||||
<b>[container.node]</b> (version for set containers).
|
||||
Two instantiations of <code>multi_index_container</code>
|
||||
have compatible nodes (i.e., the same <code>node_type</code>) if and only if
|
||||
they are of the form
|
||||
<code>multi_index_container<Value,IndexSpecifierList1,Allocator></code> and
|
||||
<code>multi_index_container<Value,IndexSpecifierList2,Allocator></code>,
|
||||
have the same number <code>I</code> of index specifiers, and, for <code>i</code> =
|
||||
<code>0</code>, ... , <code>I-1</code>, the respective <code>i</code>-th index specifiers
|
||||
refer to the same <a href="indices.html#index_catalog">type of index</a>, regardless
|
||||
of unique/non-unique variants and particular configuration type arguments.
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="nested_templates">Nested class templates</a></h4>
|
||||
|
||||
<code>template<int N> struct nth_index</code>
|
||||
@@ -644,7 +626,7 @@ of unique/non-unique variants and particular configuration type arguments.
|
||||
<code>nth_index<N>::type</code> yields the type of the
|
||||
<code>N</code>-th (0-based) index held by the <code>multi_index_container</code>, in
|
||||
the same order as they were specified.<br>
|
||||
<b>Requires:</b> <code>0 <= N < I-1</code>.
|
||||
<b>Requires:</b> <code>0 <= N < I</code>.
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename Tag> struct index</code>
|
||||
@@ -728,7 +710,7 @@ multi_index_container(<br>
|
||||
<code>EmplaceConstructible</code> into <code>multi_index_container</code>
|
||||
from <code>*first</code>.
|
||||
<code>last</code> is reachable from <code>first</code>.<br>
|
||||
<b>Effects:</b> Constructs an empty <code>multi_index_container</code> using the
|
||||
<b>Effects:</b> Constructs and empty <code>multi_index_container</code> using the
|
||||
specified argument list and allocator and fills it with
|
||||
the elements in the range [<code>first</code>,<code>last</code>).
|
||||
Insertion of each element may or may not succeed depending
|
||||
@@ -755,7 +737,7 @@ the number of elements in [<code>first</code>,<code>last</code>).<br>
|
||||
<code>multi_index_container</code>.<br>
|
||||
<b>Effects:</b> Constructs a copy of <code>x</code>, copying its
|
||||
elements as well as its internal objects (those specified
|
||||
in <code>ctor_args_list</code> and the allocator).<br>
|
||||
in <code>ctor_args_list</code> and the allocator.)<br>
|
||||
<b>Postconditions:</b> <code>*this==x</code>. The order on every index
|
||||
of the <code>multi_index_container</code> is preserved as well.<br>
|
||||
<b>Complexity:</b> <code>O(x.size()*log(x.size()) + C(x.size()))</code>.
|
||||
@@ -765,52 +747,16 @@ of the <code>multi_index_container</code> is preserved as well.<br>
|
||||
multi_index_container<Value,IndexSpecifierList,Allocator>&& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Effects:</b> Constructs a <code>multi_index_container</code> by transferring the
|
||||
<b>Effects:</b> Constructs a <code>multi_index_container</code> by moving the
|
||||
elements of <code>x</code> and copying its internal objects (those specified
|
||||
in <code>ctor_args_list</code> and the allocator).<br>
|
||||
in <code>ctor_args_list</code> and the allocator.)<br>
|
||||
<b>Postconditions:</b> If <code>x==y</code> just
|
||||
before the movement, <code>*this==y</code>. The order on every index
|
||||
of the <code>multi_index_container</code> is preserved as well.<br>
|
||||
<b>Complexity:</b> Constant.
|
||||
</blockquote>
|
||||
|
||||
<code>multi_index_container(<br>
|
||||
const multi_index_container<Value,IndexSpecifierList,Allocator>& x,<br>
|
||||
const allocator_type& al);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>Value</code> is <code>CopyInsertable</code> into
|
||||
<code>multi_index_container</code>.<br>
|
||||
<b>Effects:</b> Constructs a copy of <code>x</code>, copying its
|
||||
elements and its internal objects (those specified
|
||||
in <code>ctor_args_list</code>) and using a copy of the allocator
|
||||
<code>al</code> provided.<br>
|
||||
<b>Postconditions:</b> <code>*this==x</code>. The order on every index
|
||||
of the <code>multi_index_container</code> is preserved as well.<br>
|
||||
<b>Complexity:</b> <code>O(x.size()*log(x.size()) + C(x.size()))</code>.
|
||||
</blockquote>
|
||||
|
||||
<code>multi_index_container(<br>
|
||||
multi_index_container<Value,IndexSpecifierList,Allocator>&& x,<br>
|
||||
const allocator_type& al);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>Value</code> is <code>MoveInsertable</code> into
|
||||
<code>multi_index_container</code>.<br>
|
||||
<b>Effects:</b> Constructs a <code>multi_index_container</code> by transferring/moving
|
||||
the elements of <code>x</code>, copying its internal objects (those specified
|
||||
in <code>ctor_args_list</code>) and using a copy of the allocator
|
||||
<code>al</code> provided. If <code>x.get_allocator()==al</code>, elements are transferred
|
||||
(no constructions involved), otherwise they are move constructed from <code>x</code>.<br>
|
||||
<b>Postconditions:</b> If <code>x==y</code> just
|
||||
before the movement, <code>*this==y</code>. The order on every index
|
||||
of the <code>multi_index_container</code> is preserved as well.<br>
|
||||
<b>Complexity:</b> Constant if <code>x.get_allocator()==al</code>, otherwise
|
||||
<code>O(x.size()*log(x.size()) + C(x.size()))</code>.
|
||||
</blockquote>
|
||||
|
||||
<code>~multi_index_container()</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Effects:</b> Destroys the <code>multi_index_container</code> and all the elements
|
||||
contained. The order in which the elements are destroyed is not specified.<br>
|
||||
@@ -823,12 +769,8 @@ contained. The order in which the elements are destroyed is not specified.<br>
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>Value</code> is <code>CopyInsertable</code> into
|
||||
<code>multi_index_container</code>.<br>
|
||||
<b>Effects:</b> Replaces the elements and internal objects (those specified
|
||||
in <code>ctor_args_list</code>) of the <code>multi_index_container</code>
|
||||
with copies from <code>x</code>. The internal allocator is replaced with a
|
||||
copy of <code>x.get_allocator()</code> if and only if
|
||||
<code>std::allocator_traits<allocator_type>::propagate_on_container_copy_assignment::value</code>
|
||||
is <code>true</code>.<br>
|
||||
<b>Effects:</b> Replaces the elements and internal objects of the <code>multi_index_container</code>
|
||||
with copies from <code>x</code>.<br>
|
||||
<b>Postconditions:</b> <code>*this==x</code>. The order on every index
|
||||
of the <code>multi_index_container</code> is preserved as well.<br>
|
||||
<b>Returns:</b> <code>*this</code>.<br>
|
||||
@@ -842,27 +784,14 @@ of the types of <code>ctor_args_list</code> do not throw.
|
||||
multi_index_container<Value,IndexSpecifierList,Allocator>&& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> If <code>std::allocator_traits<allocator_type>::propagate_on_container_move_assignment::value</code>
|
||||
is <code>true</code>, <code>Value</code> is <code>MoveInsertable</code> into
|
||||
<code>multi_index_container</code>.<br>
|
||||
<b>Effects:</b> Replaces the elements of <code>multi_index_container</code>
|
||||
with those of <code>x</code> or with copies move-constructed from those of <code>x</code>.
|
||||
Replaces the internal objects (those specified
|
||||
in <code>ctor_args_list</code>) with copies from the
|
||||
corresponding objects in <code>x</code>. Replaces the internal allocator with a
|
||||
copy of <code>x.get_allocator()</code> if and only if
|
||||
<code>std::allocator_traits<allocator_type>::propagate_on_container_move_assignment::value</code>
|
||||
is <code>true</code>.
|
||||
Elements of <code>x</code> are transferred (no constructions involved) if and only if
|
||||
<code>x.get_allocator()</code> is copied or is equal to the previous value of the internal
|
||||
allocator.
|
||||
<br>
|
||||
with those of <code>x</code> and its internal objects with copies from the
|
||||
corresponding objects in <code>x</code>.<br>
|
||||
<b>Postconditions:</b> If <code>x==y</code> just
|
||||
before the movement, <code>*this==y</code>. The order on every index
|
||||
of the <code>multi_index_container</code> is preserved as well.<br>
|
||||
<b>Returns:</b> <code>*this</code>.<br>
|
||||
<b>Complexity:</b> <code>O(n)</code> if elements of <code>x</code> are transferred,
|
||||
otherwise <code>O(n + x.size()*log(x.size()) + C(x.size()))</code>.<br>
|
||||
<b>Complexity:</b> <code>O(n)</code>.<br>
|
||||
<b>Exception safety:</b> Strong, provided the copy and assignment operations
|
||||
of the types of <code>ctor_args_list</code> do not throw.
|
||||
</blockquote>
|
||||
@@ -873,7 +802,7 @@ of the types of <code>ctor_args_list</code> do not throw.
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>Value</code> is <code>CopyInsertable</code> into
|
||||
<code>multi_index_container</code>.<br>
|
||||
<b>Effects:</b> Replaces the elements of the <code>multi_index_container</code>
|
||||
<b>Effects:</b> Replaces the elements the <code>multi_index_container</code>
|
||||
with copies of the elements of <code>list</code>, inserted in the specified order.
|
||||
Insertion of each element may or may not succeed depending
|
||||
on the acceptance by all the indices of the <code>multi_index_container</code>.<br>
|
||||
@@ -897,7 +826,7 @@ the <code>multi_index_container</code>.<br>
|
||||
<code>template<int N> typename nth_index<N>::type& get()noexcept;</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>0 <= N < I-1</code>.<br>
|
||||
<b>Requires:</b> <code>0 <= N < I</code>.<br>
|
||||
<b>Effects:</b> Returns a reference to the
|
||||
<code>nth_index<N>::type</code> index held by <code>*this</code>.<br>
|
||||
<b>Complexity:</b> Constant.<br>
|
||||
@@ -906,7 +835,7 @@ the <code>multi_index_container</code>.<br>
|
||||
<code>template<int N> const typename nth_index<N>::type& get()const noexcept;</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>0 <= N < I-1</code>.<br>
|
||||
<b>Requires:</b> <code>0 <= N < I</code>.<br>
|
||||
<b>Effects:</b> Returns a <code>const</code> reference to the
|
||||
<code>nth_index<N>::type</code> index held by <code>*this</code>.<br>
|
||||
<b>Complexity:</b> Constant.<br>
|
||||
@@ -952,10 +881,10 @@ are <i>equivalent</i> if:
|
||||
typename nth_index<N>::type::iterator project(IteratorType it);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>0 <= N < I-1</code>. <code>IteratorType</code>
|
||||
<b>Requires:</b> <code>0 <= N < I</code>. <code>IteratorType</code>
|
||||
belongs to <code>iterator_type_list</code>. <code>it</code> is a valid
|
||||
iterator of some index of <code>*this</code> (i.e. does not refer to some
|
||||
other <code>multi_index_container</code>).<br>
|
||||
other <code>multi_index_container</code>.)<br>
|
||||
<b>Effects:</b> Returns an <code>nth_index<N>::type::iterator</code>
|
||||
equivalent to <code>it</code>.<br>
|
||||
<b>Complexity:</b> Constant.<br>
|
||||
@@ -966,7 +895,7 @@ equivalent to <code>it</code>.<br>
|
||||
typename nth_index<N>::type::const_iterator project(IteratorType it)const;</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>0 <= N < I-1</code>. <code>IteratorType</code>
|
||||
<b>Requires:</b> <code>0 <= N < I</code>. <code>IteratorType</code>
|
||||
belongs to <code>const_iterator_type_list</code> or
|
||||
<code>iterator_type_list</code>. <code>it</code> is a
|
||||
valid (constant or non-constant) iterator of some index of <code>*this</code>
|
||||
@@ -985,7 +914,7 @@ typename index<Tag>::type::iterator project(IteratorType it);</code>
|
||||
<code>index<Tag>::type</code> is valid. <code>IteratorType</code>
|
||||
belongs to <code>iterator_type_list</code>. <code>it</code> is a valid
|
||||
iterator of some index of <code>*this</code> (i.e. does not refer to some
|
||||
other <code>multi_index_container</code>).<br>
|
||||
other <code>multi_index_container</code>.)<br>
|
||||
<b>Effects:</b> Returns an <code>index<Tag>::type::iterator</code>
|
||||
equivalent to <code>it</code>.<br>
|
||||
<b>Complexity:</b> Constant.<br>
|
||||
@@ -1001,7 +930,7 @@ typename index<Tag>::type::const_iterator project(IteratorType it)const;</cod
|
||||
belongs to <code>const_iterator_type_list</code> or
|
||||
<code>iterator_type_list</code>. <code>it</code> is a valid
|
||||
(constant or non-constant) iterator of some index of <code>*this</code>
|
||||
(i.e. does not refer to some other <code>multi_index_container</code>).<br>
|
||||
(i.e. does not refer to some other <code>multi_index_container</code>.)<br>
|
||||
<b>Effects:</b> Returns an <code>index<Tag>::type::const_iterator</code>
|
||||
iterator equivalent to <code>it</code>.<br>
|
||||
<b>Complexity:</b> Constant.<br>
|
||||
@@ -1043,7 +972,7 @@ output archive (XML archive) <code>ar</code>.
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>Value</code> is serializable (XML-serializable). Additionally,
|
||||
each of the indices of <code>m</code> can impose other requirements.<br>
|
||||
each of the indices of <code>m</code> can impose another requirements.<br>
|
||||
<b>Exception safety:</b> Strong with respect to <code>m</code>. If an exception
|
||||
is thrown, <code>ar</code> may be left in an inconsistent state.
|
||||
</blockquote>
|
||||
@@ -1053,7 +982,7 @@ input archive (XML archive) <code>ar</code>.
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>Value</code> is serializable (XML-serializable). Additionally,
|
||||
each of the indices of <code>m'</code> can impose other requirements.<br>
|
||||
each of the indices of <code>m'</code> can impose another requirements.<br>
|
||||
<b>Exception safety:</b> Basic. If an exception is thrown, <code>ar</code> may be
|
||||
left in an inconsistent state.
|
||||
</blockquote>
|
||||
@@ -1072,9 +1001,9 @@ Index reference
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised June 27th 2026</p>
|
||||
<p>Revised April 13th 2018</p>
|
||||
|
||||
<p>© Copyright 2003-2026 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2018 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+10
-231
@@ -42,7 +42,6 @@ Ranked indices
|
||||
<ul>
|
||||
<li><a href="#complexity_signature">Complexity signature</a></li>
|
||||
<li><a href="#instantiation_types">Instantiation types</a></li>
|
||||
<li><a href="#types">Nested types</a></li>
|
||||
<li><a href="#constructors">Constructors, copy and assignment</a></li>
|
||||
<li><a href="#iterators">Iterators</a></li>
|
||||
<li><a href="#modifiers">Modifiers</a></li>
|
||||
@@ -196,13 +195,9 @@ together, with minor differences explicitly stated when they exist.
|
||||
Except where noted or if the corresponding interface does not exist,
|
||||
ordered indices (both unique and non-unique) satisfy the C++ requirements
|
||||
for associative containers at <b>[associative.reqmts]</b>
|
||||
(supporting unique and equivalent keys, respectively).
|
||||
Iterators (including to the end of the index) and pointers and references to an element
|
||||
remain valid during the lifetime of the associated container (which can change
|
||||
upon swapping), or until the referred-to element is erased or extracted;
|
||||
pointers and references to an extracted element, but not so for iterators,
|
||||
become valid again once the element is re-inserted.
|
||||
We only provide descriptions of those types and operations that
|
||||
(supporting unique and equivalent keys, respectively.)
|
||||
Accordingly, validity of iterators and references to elements is
|
||||
preserved. We only provide descriptions of those types and operations that
|
||||
do not exactly conform to or are not mandated by the standard requirements.
|
||||
</p>
|
||||
|
||||
@@ -242,8 +237,6 @@ do not exactly conform to or are not mandated by the standard requirements.
|
||||
std::reverse_iterator<iterator></b> <span class=identifier>reverse_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>equivalent to
|
||||
std::reverse_iterator<const_iterator></b> <span class=identifier>const_reverse_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>same as owning container </b><span class=identifier>node_type</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>following [container.insert.return] spec </b><span class=identifier>insert_return_type</span><span class=special>;</span>
|
||||
|
||||
<span class=comment>// construct/copy/destroy:</span>
|
||||
|
||||
@@ -289,11 +282,6 @@ do not exactly conform to or are not mandated by the standard requirements.
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>InputIterator</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>InputIterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>InputIterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>initializer_list</span><span class=special><</span><span class=identifier>value_type</span><span class=special>></span> <span class=identifier>list</span><span class=special>);</span>
|
||||
<span class=identifier>insert_return_type</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>node_type</span><span class=special>&&</span> <span class=identifier>nh</span><span class=special>);</span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>node_type</span><span class=special>&&</span> <span class=identifier>nh</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>node_type</span> <span class=identifier>extract</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
<span class=identifier>node_type</span> <span class=identifier>extract</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>key_type</span><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>iterator</span> <span class=identifier>erase</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
<span class=identifier>size_type</span> <span class=identifier>erase</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>key_type</span><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
@@ -311,16 +299,6 @@ do not exactly conform to or are not mandated by the standard requirements.
|
||||
<span class=keyword>void</span> <span class=identifier>swap</span><span class=special>(</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>clear</span><span class=special>()</span><span class=keyword>noexcept</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span> <span class=keyword>void</span> <span class=identifier>merge</span><span class=special>(</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>pair</span><span class=special><</span><span class=identifier>iterator</span><span class=special>,</span><span class=keyword>bool</span><span class=special>></span> <span class=identifier>merge</span><span class=special>(</span>
|
||||
<span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>i</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>merge</span><span class=special>(</span>
|
||||
<span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>first</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
|
||||
<span class=comment>// observers:</span>
|
||||
|
||||
<span class=identifier>key_from_value</span> <span class=identifier>key_extractor</span><span class=special>()</span><span class=keyword>const</span><span class=special>;</span>
|
||||
@@ -340,11 +318,6 @@ do not exactly conform to or are not mandated by the standard requirements.
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>CompatibleCompare</span><span class=special>></span>
|
||||
<span class=identifier>size_type</span> <span class=identifier>count</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>CompatibleCompare</span><span class=special>&</span> <span class=identifier>comp</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>></span>
|
||||
<span class=keyword>bool</span> <span class=identifier>contains</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>CompatibleCompare</span><span class=special>></span>
|
||||
<span class=keyword>bool</span> <span class=identifier>contains</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>CompatibleCompare</span><span class=special>&</span> <span class=identifier>comp</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>></span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>lower_bound</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>CompatibleCompare</span><span class=special>></span>
|
||||
@@ -443,7 +416,7 @@ section</a>. The complexity signature of ordered indices is:
|
||||
<ul>
|
||||
<li>copying: <code>c(n)=n*log(n)</code>,</li>
|
||||
<li>insertion: <code>i(n)=log(n)</code>,</li>
|
||||
<li>hinted insertion: <code>h(n)=1</code> (amortized constant) if the hint element
|
||||
<li>hinted insertion: <code>h(n)=1</code> (constant) if the hint element
|
||||
is immediately after the point of insertion, <code>h(n)=log(n)</code> otherwise,</li>
|
||||
<li>deletion: <code>d(n)=1</code> (amortized constant),</li>
|
||||
<li>replacement: <code>r(n)=1</code> (constant) if the element position does not
|
||||
@@ -476,16 +449,6 @@ must be a model of <a href="key_extraction.html#key_extractors">
|
||||
on elements of <code>KeyFromValue::result_type</code>.
|
||||
</p>
|
||||
|
||||
<h4><a name="types">Nested types</a></h4>
|
||||
|
||||
<code>iterator<br>
|
||||
const_iterator</code>
|
||||
|
||||
<blockquote>
|
||||
These types depend only on <code>node_type</code> and the position of
|
||||
the index in the <code>multi_index_container</code>.
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="constructors">Constructors, copy and assignment</a></h4>
|
||||
|
||||
<p>
|
||||
@@ -672,89 +635,10 @@ to which this index belongs if
|
||||
</pre></blockquote>
|
||||
</blockquote>
|
||||
|
||||
<code>insert_return_type insert(node_type&& nh);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>nh.empty() || get_allocator()==nh.get_allocator()</code>.<br>
|
||||
<b>Effects:</b> Does nothing if <code>nh</code> is empty; otherwise,
|
||||
inserts the node owned by <code>nh</code> into the
|
||||
<code>multi_index_container</code> to which the index belongs if
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists with
|
||||
equivalent key,</li>
|
||||
<li>AND insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
</ul>
|
||||
<b>Postconditions:</b> <code>nh</code> is empty.<br>
|
||||
<b>Returns:</b> A value <code>p</code> of type <code>insert_return_type</code>.
|
||||
If <code>nh</code> is empty, <code>p.position</code> is <code>end()</code>,
|
||||
<code>p.inserted</code> is <code>false</code> and <code>p.node</code> is empty;
|
||||
on successful insertion, <code>p.position</code> points to the element inserted,
|
||||
<code>p.inserted</code> is <code>true</code> and <code>p.node</code>
|
||||
is empty;
|
||||
if the insertion failed, <code>p.position</code> points to an element that caused
|
||||
the insertion to be banned, <code>p.inserted</code> is <code>false</code> and
|
||||
<code>p.node</code> owns the original node.
|
||||
Note that more than one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> <code>O(I(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong. If an exception
|
||||
is thrown, <code>nh</code> is not changed.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>iterator insert(const_iterator position,node_type&& nh);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>nh.empty() || get_allocator()==nh.get_allocator()</code>.
|
||||
<code>position</code> is a valid iterator of the index.<br>
|
||||
<b>Effects:</b> Does nothing if <code>nh</code> is empty; otherwise,
|
||||
inserts the node owned by <code>nh</code> into the
|
||||
<code>multi_index_container</code> to which the index belongs if
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists with
|
||||
equivalent key,</li>
|
||||
<li>AND insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
</ul>
|
||||
<code>position</code> is used as a hint to improve the efficiency of the
|
||||
operation. If successful, insertion happens as close as possible to the
|
||||
location just prior to <code>position</code>.<br>
|
||||
<b>Postconditions:</b> <code>nh</code> is empty if insertion succeeds,
|
||||
and is not changed otherwise.<br>
|
||||
<b>Returns:</b> <code>end()</code> if <code>nh</code> is empty.
|
||||
On successful insertion, an iterator to the newly inserted
|
||||
element; otherwise, an iterator to an element that caused the insertion to be
|
||||
banned. Note that more than one element can be causing insertion not to be
|
||||
allowed.<br>
|
||||
<b>Complexity:</b> <code>O(H(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong. If an exception
|
||||
is thrown, <code>nh</code> is not changed.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>node_type extract(const_iterator position);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>position</code> is a valid dereferenceable iterator
|
||||
of the index.<br>
|
||||
<b>Effects:</b> Extracts the node of the element pointed to by <code>position</code>.<br>
|
||||
<b>Returns:</b> A node handle owning the extracted node.<br>
|
||||
<b>Complexity:</b> <code>O(D(n))</code>.<br>
|
||||
<b>Exception safety:</b> <code>nothrow</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>node_type extract(const key_type& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Effects:</b> Extracts the node of the first element
|
||||
with key equivalent to <code>x</code>, if there is any.<br>
|
||||
<b>Returns:</b> A node handle owning the extracted node, or empty otherwise.<br>
|
||||
<b>Complexity:</b> <code>O(log(n) + D(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>iterator erase(iterator position);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>position</code> is a valid dereferenceable iterator
|
||||
<b>Requires:</b> <code>position</code> is a valid dereferenceable iterator
|
||||
of the index.<br>
|
||||
<b>Effects:</b> Deletes the element pointed to by <code>position</code>.<br>
|
||||
<b>Returns:</b> An iterator pointing to the element immediately following
|
||||
@@ -932,89 +816,6 @@ with <code>mod'</code> and <code>back</code> defined in such a way that
|
||||
<code>key</code> is the internal <code>KeyFromValue</code> object of the index.
|
||||
</blockquote>
|
||||
|
||||
<a name="merge"><code>template<typename Index> void merge(Index&& x);</code></a>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>. <code>get_allocator()==x.get_allocator()</code>.<br>
|
||||
<b>Effects:</b>
|
||||
<blockquote><pre>
|
||||
<span class=identifier>merge</span><span class=special>(</span><span class=identifier>x</span><span class=special>,</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>begin</span><span class=special>(),</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>end</span><span class=special>());</span>
|
||||
</pre></blockquote>
|
||||
</blockquote>
|
||||
|
||||
<code>
|
||||
template<typename Index> std::pair<iterator,bool> merge(<br>
|
||||
Index&& x,typename std::remove_reference_t<Index>::const_iterator i);
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>. <code>get_allocator()==x.get_allocator()</code>.
|
||||
<code>i</code> is a valid dereferenceable iterator of <code>x</code>.<br>
|
||||
<b>Effects:</b> Does nothing if the source and destination containers are the same;
|
||||
otherwise, transfers the node of the element referred to by <code>i</code> into the
|
||||
<code>multi_index_container</code> to which the destination index belongs if
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists with
|
||||
equivalent key,</li>
|
||||
<li>AND insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
</ul>
|
||||
Note that no element is copied or destroyed in the process.<br>
|
||||
<b>Postconditions:</b> If transfer succeeds, for any index in the source container
|
||||
having the same <code>iterator</code>/<code>const_iterator</code> types as the corresponding
|
||||
index in the destination container, iterators referring to <code>*i</code>
|
||||
remain valid and behave as iterators of the destination index.<br>
|
||||
<b>Returns:</b> The return value is a pair <code>p</code>. <code>p.second</code>
|
||||
is <code>true</code> if and only if transfer took place or the source and destination
|
||||
containers are the same. If <code>p.second</code> is <code>true</code>,
|
||||
<code>p.first</code> points to <code>*i</code>; otherwise, <code>p.first</code>
|
||||
points to an element that caused the insertion to be banned. Note that more than
|
||||
one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> If the source and destination containers are the same,
|
||||
constant; otherwise, <code>O(I(n)+D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> If the source and destination containers are the same,
|
||||
<code>nothrow</code>; otherwise strong.
|
||||
</blockquote>
|
||||
|
||||
<code>
|
||||
template<typename Index> void merge(<br>
|
||||
Index&& x,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator first,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator last);
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>. <code>get_allocator()==x.get_allocator()</code>.
|
||||
[<code>first</code>,<code>last</code>) is a valid range of <code>x</code>.<br>
|
||||
<b>Effects:</b> Does nothing if the source and destination containers are the same;
|
||||
otherwise, for each node in [<code>first</code>,<code>last</code>), in this order,
|
||||
the node is transferred to the <code>multi_index_container</code> to which the
|
||||
destination index belongs if
|
||||
<ul>
|
||||
<li>the index is non-unique OR no other element exists with
|
||||
equivalent key,</li>
|
||||
<li>AND insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
</ul>
|
||||
Note that no element is copied or destroyed in the process.<br>
|
||||
<b>Postconditions:</b> For any index in the source container having the same
|
||||
<code>iterator</code>/<code>const_iterator</code> types as the corresponding
|
||||
index in the destination container, iterators referring to the transferred elements
|
||||
remain valid and behave as iterators of the destination index.<br>
|
||||
<b>Complexity:</b> If the source and destination containers are the same,
|
||||
constant; otherwise, <code>O(m*(I(n+m)+D(x.size())))</code>, where
|
||||
<code>m</code> is the number of elements in [<code>first</code>,
|
||||
<code>last</code>).<br>
|
||||
<b>Exception safety:</b> If the source and destination containers are the same,
|
||||
<code>nothrow</code>; otherwise basic.
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="observers">Observers</a></h4>
|
||||
|
||||
<p>Apart from standard <code>key_comp</code> and <code>value_comp</code>,
|
||||
@@ -1104,8 +905,8 @@ is a compatible extension of <code>key_compare</code>.<br>
|
||||
<b>Complexity:</b> <code>O(log(n))</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename CompatibleKey><br>
|
||||
size_type count(const CompatibleKey& x)const;
|
||||
<code>template<typename CompatibleKey> size_type<br>
|
||||
count(const CompatibleKey& x)const;
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
@@ -1126,28 +927,6 @@ is a compatible extension of <code>key_compare</code>.<br>
|
||||
<b>Complexity:</b> <code>O(log(n) + count(x,comp))</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename CompatibleKey><br>
|
||||
bool contains(const CompatibleKey& x)const;
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>CompatibleKey</code> is a compatible key of
|
||||
<code>key_compare</code>.<br>
|
||||
<b>Effects:</b> Returns <code>true</code> iff there is some element with key equivalent to <code>x</code>.<br>
|
||||
<b>Complexity:</b> <code>O(log(n))</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename CompatibleKey,typename CompatibleCompare><br>
|
||||
bool contains(const CompatibleKey& x,const CompatibleCompare& comp)const;
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> (<code>CompatibleKey</code>, <code>CompatibleCompare</code>)
|
||||
is a compatible extension of <code>key_compare</code>.<br>
|
||||
<b>Effects:</b> Returns <code>true</code> iff there is some element with key equivalent to <code>x</code>.<br>
|
||||
<b>Complexity:</b> <code>O(log(n))</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename CompatibleKey><br>
|
||||
iterator lower_bound(const CompatibleKey& x)const;
|
||||
</code>
|
||||
@@ -1324,7 +1103,7 @@ Operation: loading of an <code>iterator</code> or <code>const_iterator</code>
|
||||
then <code>*it'</code> is the restored copy of <code>*it</code>, otherwise
|
||||
<code>it'==end()</code>.<br>
|
||||
<b>Note:</b> It is allowed that <code>it</code> be a <code>const_iterator</code>
|
||||
and the restored <code>it'</code> an <code>iterator</code>, or vice versa.
|
||||
and the restored <code>it'</code> an <code>iterator</code>, or viceversa.
|
||||
</blockquote>
|
||||
|
||||
<hr>
|
||||
@@ -1341,9 +1120,9 @@ Ranked indices
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised February 5th 2022</p>
|
||||
<p>Revised August 24th 2017</p>
|
||||
|
||||
<p>© Copyright 2003-2022 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2017 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+69
-192
@@ -40,7 +40,6 @@ Key extraction
|
||||
<ul>
|
||||
<li><a href="#complexity_signature">Complexity signature</a></li>
|
||||
<li><a href="#instantiation_types">Instantiation types</a></li>
|
||||
<li><a href="#types">Nested types</a></li>
|
||||
<li><a href="#constructors">Constructors, copy and assignment</a></li>
|
||||
<li><a href="#iterators">Iterators</a></li>
|
||||
<li><a href="#capacity">Capacity operations</a></li>
|
||||
@@ -159,12 +158,8 @@ random access indices includes that of
|
||||
<a href="seq_indices.html">sequenced indices</a>, with differences in
|
||||
the complexity of the operations, plus extra operations for
|
||||
positional access (<code>operator[]</code> and <code>at()</code>) and
|
||||
for capacity handling.
|
||||
Iterators (including to the end of the index) and pointers and references to an element
|
||||
remain valid during the lifetime of the associated container (which can change
|
||||
upon swapping) regardless of the capacity status, or until the referred-to element
|
||||
is erased or extracted; pointers and references to an extracted element,
|
||||
but not so for iterators, become valid again once the element is re-inserted.
|
||||
for capacity handling. Validity of iterators and references to elements
|
||||
is preserved in all operations, regardless of the capacity status.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
@@ -178,7 +173,7 @@ plus the requirements for <code>std::list</code> specific list operations at
|
||||
have <code>data</code> member functions.
|
||||
</li>
|
||||
|
||||
<li>The complexities of some operations, notably insertion and deletion, differ
|
||||
<li>The complexity of some operations, notably insertion and deletion, differ
|
||||
from those of <code>std::vector</code>.
|
||||
</li>
|
||||
<li>Unlike as in <code>std::vector</code>, insertions into a random access index
|
||||
@@ -186,8 +181,8 @@ plus the requirements for <code>std::list</code> specific list operations at
|
||||
of the operations provided with respect to their analogues in
|
||||
<code>std::vector</code>.
|
||||
</li>
|
||||
<li>Elements in a random access index are not mutable, and can only be changed
|
||||
in place by means of <a href="#replace"><code>replace</code></a> and
|
||||
<li>Elements in a randon access index are not mutable, and can only be changed
|
||||
by means of <a href="#replace"><code>replace</code></a> and
|
||||
<a href="#modify"><code>modify</code></a> member functions.
|
||||
</li>
|
||||
<li><code>push_front</code> and <code>pop_front</code> are provided for
|
||||
@@ -224,8 +219,6 @@ plus the requirements for <code>std::list</code> specific list operations at
|
||||
std::reverse_iterator<iterator></b> <span class=identifier>reverse_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>equivalent to
|
||||
std::reverse_iterator<const_iterator></b> <span class=identifier>const_reverse_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>same as owning container </b><span class=identifier>node_type</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>following [container.insert.return] spec </b><span class=identifier>insert_return_type</span><span class=special>;</span>
|
||||
|
||||
<span class=comment>// construct/copy/destroy:</span>
|
||||
|
||||
@@ -298,9 +291,6 @@ plus the requirements for <code>std::list</code> specific list operations at
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>InputIterator</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>InputIterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>InputIterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>initializer_list</span><span class=special><</span><span class=identifier>value_type</span><span class=special>></span> <span class=identifier>list</span><span class=special>);</span>
|
||||
<span class=identifier>insert_return_type</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>node_type</span><span class=special>&&</span> <span class=identifier>nh</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>node_type</span> <span class=identifier>extract</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>iterator</span> <span class=identifier>erase</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>erase</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
@@ -317,16 +307,10 @@ plus the requirements for <code>std::list</code> specific list operations at
|
||||
|
||||
<span class=comment>// list operations:</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span> <span class=keyword>void</span> <span class=identifier>splice</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>pair</span><span class=special><</span><span class=identifier>iterator</span><span class=special>,</span><span class=keyword>bool</span><span class=special>></span> <span class=identifier>splice</span><span class=special>(</span>
|
||||
<span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>i</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>splice</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>splice</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span><span class=identifier>iterator</span> <span class=identifier>i</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>splice</span><span class=special>(</span>
|
||||
<span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>first</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span><span class=identifier>iterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
|
||||
<span class=keyword>void</span> <span class=identifier>remove</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>value_type</span><span class=special>&</span> <span class=identifier>value</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Predicate</span><span class=special>></span> <span class=keyword>void</span> <span class=identifier>remove_if</span><span class=special>(</span><span class=identifier>Predicate</span> <span class=identifier>pred</span><span class=special>);</span>
|
||||
@@ -439,7 +423,7 @@ of the complexity formulas:
|
||||
|
||||
<p>
|
||||
(<code>shl</code> and <code>rel</code> stand for <i>shift left</i> and
|
||||
<i>relocate</i>, respectively).
|
||||
<i>relocate</i>, respectively.)
|
||||
</p>
|
||||
|
||||
<h4><a name="instantiation_types">Instantiation types</a></h4>
|
||||
@@ -457,16 +441,6 @@ index specifier. Instantiations are dependent on the following types:
|
||||
<a href="indices.html#tag"><code>tag</code></a>.
|
||||
</p>
|
||||
|
||||
<h4><a name="types">Nested types</a></h4>
|
||||
|
||||
<code>iterator<br>
|
||||
const_iterator</code>
|
||||
|
||||
<blockquote>
|
||||
These types depend only on <code>node_type</code> and the position of
|
||||
the index in the <code>multi_index_container</code>.
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="constructors">Constructors, copy and assignment</a></h4>
|
||||
|
||||
<p>
|
||||
@@ -550,7 +524,7 @@ const_iterator iterator_to(const value_type& x)const;</code>
|
||||
<code>size()<c</code>, back insertions happen in constant time (the
|
||||
general case as described by
|
||||
<a href="#complexity_signature"><code>i(n)</code></a> is <i>amortized</i>
|
||||
constant time).<br>
|
||||
constant time.)<br>
|
||||
<b>Note:</b> Validity of iterators and references to elements
|
||||
is preserved in all insertions, regardless of the capacity status.
|
||||
</blockquote>
|
||||
@@ -590,7 +564,7 @@ into <code>multi_index_container</code>.<br>
|
||||
elements (first version) or copies of <code>x</code> (second version) at the end of
|
||||
the index. If <code>n<size()</code>, erases the last <code>size()-n</code> elements.<br>
|
||||
<b>Note:</b> If an expansion is requested, the size of the index is not guaranteed
|
||||
to be <code>n</code> after this operation (other indices may ban insertions).
|
||||
to be <code>n</code> after this operation (other indices may ban insertions.)
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="modifiers">Modifiers</a></h4>
|
||||
@@ -671,7 +645,7 @@ is <code>true</code> if and only if insertion took place. On successful insertio
|
||||
<code>p.first</code> points to the element inserted; otherwise, <code>p.first</code>
|
||||
points to an element that caused the insertion to be banned. Note that more than
|
||||
one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> <code>O(shl(end()-position,1) + I(n))</code>.<br>
|
||||
<b>Complexity:</b> <code>O(I(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong.<br>
|
||||
</blockquote>
|
||||
|
||||
@@ -692,7 +666,7 @@ is <code>true</code> if and only if insertion took place. On successful
|
||||
insertion, <code>p.first</code> points to the element inserted; otherwise,
|
||||
<code>p.first</code> points to an element that caused the insertion to be banned.
|
||||
Note that more than one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> <code>O(shl(end()-position,1) + I(n))</code>.<br>
|
||||
<b>Complexity:</b> <code>O(I(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong.
|
||||
</blockquote>
|
||||
|
||||
@@ -738,40 +712,6 @@ where <code>m</code> is the number of elements in
|
||||
</pre></blockquote>
|
||||
</blockquote>
|
||||
|
||||
<code>insert_return_type insert(const_iterator position,node_type&& nh);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>nh.empty() || get_allocator()==nh.get_allocator()</code>.<br>
|
||||
<b>Effects:</b> Does nothing if <code>nh</code> is empty; otherwise,
|
||||
inserts the node owned by <code>nh</code> before <code>position</code> if insertion
|
||||
is allowed by all other indices of the <code>multi_index_container</code>.<br>
|
||||
<b>Postconditions:</b> <code>nh</code> is empty.<br>
|
||||
<b>Returns:</b> A value <code>p</code> of type <code>insert_return_type</code>.
|
||||
If <code>nh</code> is empty, <code>p.position</code> is <code>end()</code>,
|
||||
<code>p.inserted</code> is <code>false</code> and <code>p.node</code> is empty;
|
||||
on successful insertion, <code>p.position</code> points to the element inserted,
|
||||
<code>p.inserted</code> is <code>true</code> and <code>p.node</code>
|
||||
is empty;
|
||||
if the insertion failed, <code>p.position</code> points to an element that caused
|
||||
the insertion to be banned, <code>p.inserted</code> is <code>false</code> and
|
||||
<code>p.node</code> owns the original node.
|
||||
Note that more than one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> <code>O(shl(end()-position,1) + I(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong. If an exception
|
||||
is thrown, <code>nh</code> is not changed.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>node_type extract(const_iterator position);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>position</code> is a valid dereferenceable iterator
|
||||
of the index.<br>
|
||||
<b>Effects:</b> Extracts the node of the element pointed to by <code>position</code>.<br>
|
||||
<b>Returns:</b> A node handle owning the extracted node.<br>
|
||||
<b>Complexity:</b> <code>O(D(n))</code>.<br>
|
||||
<b>Exception safety:</b> <code>nothrow</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>iterator erase(iterator position);</code>
|
||||
|
||||
<blockquote>
|
||||
@@ -892,116 +832,56 @@ The syntax and behavior of these operations exactly matches those
|
||||
of sequenced indices, but the associated complexity bounds differ in general.
|
||||
</p>
|
||||
|
||||
<code>template<typename Index> void splice(const_iterator position,Index&& x);</code>
|
||||
<code>void splice(iterator position,<b>index class name</b>& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>.
|
||||
<code>position</code> is a valid iterator of the index, and must be exactly <code>end()</code>
|
||||
if the source and destination containers are the same.<br>
|
||||
<b>Effects:</b>
|
||||
<blockquote><pre>
|
||||
<span class=identifier>splice</span><span class=special>(</span><span class=identifier>position</span><span class=special>,</span><span class=identifier>x</span><span class=special>,</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>begin</span><span class=special>(),</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>end</span><span class=special>());</span>
|
||||
</pre></blockquote>
|
||||
<b>Requires:</b> <code>position</code> is a valid iterator of the index.
|
||||
<code>&x!=this</code>.<br>
|
||||
<b>Effects:</b> Inserts the contents of <code>x</code> before <code>position</code>,
|
||||
in the same order as they were in <code>x</code>. Those elements successfully
|
||||
inserted are erased from <code>x</code>.<br>
|
||||
<b>Complexity:</b> <code>O(shl(end()-position,x.size()) + x.size()*I(n+x.size()) + x.size()*D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> Basic.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>
|
||||
template<typename Index> std::pair<iterator,bool> splice(<br>
|
||||
const_iterator position,Index&& x,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator i);
|
||||
</code>
|
||||
<code>void splice(iterator position,<b>index class name</b>& x,iterator i);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>.
|
||||
If <code>get_allocator()!=x.get_allocator()</code>,
|
||||
<code>value_type</code> must be <code>CopyInsertable</code> into the destination
|
||||
<code>multi_index_container</code>.
|
||||
<code>position</code> is a valid iterator of the index.
|
||||
<code>i</code> is a valid dereferenceable iterator of <code>x</code>.<br>
|
||||
<b>Effects:</b>
|
||||
<ul>
|
||||
<li><b>(Same container)</b> if the source and destination containers are the same, repositions
|
||||
the element pointed to by <code>i</code> before <code>position</code> unless both
|
||||
iterators refer to the same element.</li>
|
||||
<li><b>(Transfer splice)</b> else, if <code>get_allocator()==x.get_allocator()</code>,
|
||||
transfers the node of the element referred to by <code>i</code> into the
|
||||
destination <code>multi_index_container</code> right before <code>position</code>
|
||||
if insertion is allowed by all other indices of the <code>multi_index_container</code>.</li>
|
||||
<li><b>(Destructive splice)</b> else, insertion of <code>*i</code> is tried before
|
||||
<code>position</code>; if the operation is successful, the element is erased from <code>x</code>.
|
||||
</li>
|
||||
</ul>
|
||||
<b>Postconditions:</b> If transfer succeeds, for any index in the source container
|
||||
having the same <code>iterator</code>/<code>const_iterator</code> types as the corresponding
|
||||
index in the destination container, iterators referring to <code>*i</code>
|
||||
remain valid and behave as iterators of the destination index.<br>
|
||||
<b>Returns:</b> The return value is a pair <code>p</code>. <code>p.second</code>
|
||||
is <code>true</code> if and only if insertion (either through transfer or copy insertion)
|
||||
took place or the source and destination containers are the same.
|
||||
If <code>p.second</code> is <code>true</code>,
|
||||
<code>p.first</code> points to the inserted element or to <code>*i</code> if the
|
||||
source and destination containers are the same; otherwise, <code>p.first</code>
|
||||
points to an element that caused the insertion to be banned. Note that more than
|
||||
one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> If the source and destination containers are the same,
|
||||
<code>O(rel(position,i',i'+1))</code>, where <code>i'</code> is the projection
|
||||
of <code>i</code> into the index of <code>position</code>;
|
||||
otherwise, <code>O(shl(end()-position,1) + I(n) + D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> If the source and destination containers are the same,
|
||||
<code>nothrow</code>; otherwise strong.<br>
|
||||
<b>Implementation note:</b> The destructive variant of this operation is provided
|
||||
for reasons of backwards compatibility with previous versions of this library where
|
||||
allocator equality was not required.
|
||||
<b>Requires:</b> <code>position</code> is a valid iterator of the index.
|
||||
<code>i</code> is a valid dereferenceable iterator <code>x</code>.<br>
|
||||
<b>Effects:</b> Inserts the element pointed to by <code>i</code> before
|
||||
<code>position</code>: if insertion is successful, the element is erased from
|
||||
<code>x</code>. In the special case <code>&x==this</code>, no copy or
|
||||
deletion is performed, and the operation is always successful. If
|
||||
<code>position==i</code>, no operation is performed.<br>
|
||||
<b>Postconditions:</b> If <code>&x==this</code>, no iterator or reference
|
||||
is invalidated.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, <code>O(rel(position,i,i+1))</code>;
|
||||
otherwise <code>O(shl(end()-position,1) + I(n) + D(n))</code>.<br>
|
||||
<b>Exception safety:</b> If <code>&x==this</code>, <code>nothrow</code>;
|
||||
otherwise, strong.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>
|
||||
template<typename Index> void splice(<br>
|
||||
const_iterator position,Index&& x,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator first,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator last);
|
||||
</code>
|
||||
<code>void splice(iterator position,<b>index class name&</b> x,iterator first,iterator last);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>.
|
||||
If <code>get_allocator()!=x.get_allocator()</code>,
|
||||
<code>value_type</code> must be <code>CopyInsertable</code> into the destination
|
||||
<code>multi_index_container</code>.
|
||||
<code>position</code> is a valid iterator of the index and does not point to any element in
|
||||
[<code>first</code>,<code>last</code>).
|
||||
[<code>first</code>,<code>last</code>) is a valid range of <code>x</code>.<br>
|
||||
<b>Effects:</b>
|
||||
<ul>
|
||||
<li><b>(Same container)</b> if the source and destination containers are the same, repositions all the elements
|
||||
of [<code>first</code>,<code>last</code>), in this order, before <code>position</code>.
|
||||
</li>
|
||||
<li><b>(Transfer splice)</b> else, if <code>get_allocator()==x.get_allocator()</code>, then, for each node in
|
||||
[<code>first</code>,<code>last</code>), in this order, the node is transferred to the
|
||||
<code>multi_index_container</code> right before <code>position</code>
|
||||
if insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
<li><b>(Destructive splice)</b> else, for each element in [<code>first</code>,<code>last</code>), in this order,
|
||||
insertion is tried before <code>position</code>; if the operation is successful, the
|
||||
element is erased from <code>x</code>.
|
||||
</li>
|
||||
</ul>
|
||||
<b>Postconditions:</b> For any index in the source container having the same
|
||||
<code>iterator</code>/<code>const_iterator</code> types as the corresponding
|
||||
index in the destination container, iterators referring to the transferred elements
|
||||
remain valid and behave as iterators of the destination index.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, <code>O(rel(position,first,last))</code>;
|
||||
else, if the source and destination containers are the same, <code>O(n)</code>;
|
||||
otherwise, <code>O(shl(end()-position,m) + m*(I(n+m) + D(x.size())))</code>, where
|
||||
<code>m</code> is the number of elements in [<code>first</code>,<code>last</code>).<br>
|
||||
<b>Exception safety:</b> If the source and destination containers are the same,
|
||||
<code>nothrow</code>; otherwise basic.<br>
|
||||
<b>Implementation note:</b> The destructive variant of this operation is provided
|
||||
for reasons of backwards compatibility with previous versions of this library where
|
||||
allocator equality was not required.
|
||||
<b>Requires:</b> <code>position</code> is a valid iterator of the index.
|
||||
<code>first</code> and <code>last</code> are valid iterators of <code>x</code>.
|
||||
<code>last</code> is reachable from <code>first</code>. <code>position</code>
|
||||
is not in the range [<code>first</code>,<code>last</code>).<br>
|
||||
<b>Effects:</b> For each element in the range [<code>first</code>,<code>last</code>),
|
||||
insertion is tried before <code>position</code>; if the operation is successful,
|
||||
the element is erased from <code>x</code>. In the special case
|
||||
<code>&x==this</code>, no copy or deletion is performed, and insertions are
|
||||
always successful.<br>
|
||||
<b>Postconditions:</b> If <code>&x==this</code>, no iterator or reference
|
||||
is invalidated.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>,
|
||||
<code>O(rel(position,first,last))</code>; otherwise
|
||||
<code>O(shl(end()-position,m) + m*I(n+m) + m*D(x.size()))</code>
|
||||
where <code>m</code> is the number of elements in [<code>first</code>,<code>last</code>).<br>
|
||||
<b>Exception safety:</b> If <code>&x==this</code>, <code>nothrow</code>;
|
||||
otherwise, basic.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>void remove(const value_type& value);</code>
|
||||
@@ -1050,22 +930,20 @@ is the number of elements erased.<br>
|
||||
<code>void merge(index class name& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b>
|
||||
Either <code>get_allocator()==x.get_allocator()</code> or <code>value_type</code>
|
||||
is <code>CopyInsertable</code> into the <code>multi_index_container</code>.
|
||||
<code>std::less<value_type></code> induces a
|
||||
<b>Requires:</b> <code>std::less<value_type></code> induces a
|
||||
strict weak ordering over <code>value_type</code>.
|
||||
Both the index and <code>x</code> are sorted according to
|
||||
<code>std::less<value_type></code>.<br>
|
||||
<b>Effects:</b> Attempts to splice every element of <code>x</code> into the
|
||||
corresponding position of the index (according to the order). The resulting sequence
|
||||
<b>Effects:</b> Attempts to insert every element of <code>x</code> into the
|
||||
corresponding position of the index (according to the order). Elements
|
||||
successfully inserted are erased from <code>x</code>. The resulting sequence
|
||||
is stable, i.e. equivalent elements of either container preserve their
|
||||
relative position. In the special case <code>&x==this</code>, no operation
|
||||
is performed.<br>
|
||||
<b>Postconditions:</b> Elements in the index and remaining elements in
|
||||
<code>x</code> are sorted.
|
||||
Validity of iterators and references is preserved, except to elements removed
|
||||
from <code>x</code> if <code>get_allocator()!=x.get_allocator()</code>.<br>
|
||||
Validity of iterators to the index and of non-erased elements of <code>x</code>
|
||||
references is preserved.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, constant; otherwise
|
||||
<code>O(n + x.size()*I(n+x.size()) + x.size()*D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> If <code>&x==this</code>, <code>nothrow</code>;
|
||||
@@ -1075,20 +953,19 @@ otherwise, basic.<br>
|
||||
<code>template <typename Compare> void merge(index class name& x,Compare comp);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b>
|
||||
Either <code>get_allocator()==x.get_allocator()</code> or <code>value_type</code>
|
||||
is <code>CopyInsertable</code> into the <code>multi_index_container</code>.
|
||||
<code>Compare</code> induces a strict weak ordering over <code>value_type</code>.
|
||||
<b>Requires:</b> <code>Compare</code> induces a
|
||||
strict weak ordering over <code>value_type</code>.
|
||||
Both the index and <code>x</code> are sorted according to <code>comp</code>.<br>
|
||||
<b>Effects:</b> Attempts to splice every element of <code>x</code> into the
|
||||
corresponding position of the index (according to <code>comp</code>). The resulting
|
||||
<b>Effects:</b> Attempts to insert every element of <code>x</code> into the
|
||||
corresponding position of the index (according to <code>comp</code>).
|
||||
Elements successfully inserted are erased from <code>x</code>. The resulting
|
||||
sequence is stable, i.e. equivalent elements of either container preserve
|
||||
their relative position. In the special case <code>&x==this</code>, no
|
||||
operation is performed.<br>
|
||||
<b>Postconditions:</b> Elements in the index and remaining elements in
|
||||
<code>x</code> are sorted according to <code>comp</code>.
|
||||
Validity of iterators and references is preserved, except to elements removed
|
||||
from <code>x</code> if <code>get_allocator()!=x.get_allocator()</code>.<br>
|
||||
Validity of iterators to the index and of non-erased elements of <code>x</code>
|
||||
references is preserved.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, constant; otherwise
|
||||
<code>O(n + x.size()*I(n+x.size()) + x.size()*D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> If <code>&x==this</code>, <code>nothrow</code>;
|
||||
@@ -1223,7 +1100,7 @@ Operation: loading of an <code>iterator</code> or <code>const_iterator</code>
|
||||
then <code>*it'</code> is the restored copy of <code>*it</code>, otherwise
|
||||
<code>it'==end()</code>.<br>
|
||||
<b>Note:</b> It is allowed that <code>it</code> be a <code>const_iterator</code>
|
||||
and the restored <code>it'</code> an <code>iterator</code>, or vice versa.
|
||||
and the restored <code>it'</code> an <code>iterator</code>, or viceversa.
|
||||
</blockquote>
|
||||
|
||||
<hr>
|
||||
@@ -1240,9 +1117,9 @@ Key extraction
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised August 30th 2021</p>
|
||||
<p>Revised December 29th 2018</p>
|
||||
|
||||
<p>© Copyright 2003-2021 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2018 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
@@ -42,8 +42,6 @@ Hashed indices
|
||||
<ul>
|
||||
<li><a href="#complexity_signature">Complexity signature</a></li>
|
||||
<li><a href="#instantiation_types">Instantiation types</a></li>
|
||||
<li><a href="#types">Nested types</a></li>
|
||||
<li><a href="#set_operations">Set operations</a></li>
|
||||
<li><a href="#rank_operations">Rank operations</a></li>
|
||||
<li><a href="#serialization">Serialization</a></li>
|
||||
</ul>
|
||||
@@ -175,19 +173,16 @@ explanations on their acceptable type values.
|
||||
Ranked indices are a variation of <a href="ord_indices.html">ordered indices</a>
|
||||
providing additional capabilities for calculation of and access by rank; the <i>rank</i> of an element is the
|
||||
distance to it from the beginning of the index. Besides this extension, ranked indices replicate the
|
||||
public interface of ordered indices with the difference, complexity-wise, that
|
||||
<a href="#complexity_signature">hinted insertion</a> and <a href="#complexity_signature">deletion</a>
|
||||
are done in logarithmic rather than constant time. Also, execution times and memory consumption are
|
||||
expected to be poorer due to the internal bookkeeping needed to maintain rank-related information
|
||||
(an exception being <a href="#count"><code>count</code> operations</a>, which are actually faster).
|
||||
public interface of ordered indices with the difference, complexity-wise, that <a href="#complexity_signature">deletion</a>
|
||||
is done in logarithmic rather than constant time. Also, execution times and memory consumption are
|
||||
expected to be poorer due to the internal bookkeeping needed to maintain rank-related information.
|
||||
As with ordered indices, ranked indices can be unique (no duplicate elements are allowed)
|
||||
or non-unique: either version is associated to a different index specifier, but
|
||||
the interface of both index types is the same.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
In what follows, we only describe the extra operations provided by ranked indices or those
|
||||
operations with improved performance: for the
|
||||
In what follows, we only describe the extra operations provided by ranked indices: for the
|
||||
rest refer to the <a href="ord_indices.html#ord_indices">documentation</a> for ordered
|
||||
indices, bearing in mind the occasional differences in complexity.
|
||||
</p>
|
||||
@@ -228,8 +223,6 @@ indices, bearing in mind the occasional differences in complexity.
|
||||
std::reverse_iterator<iterator></b> <span class=identifier>reverse_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>equivalent to
|
||||
std::reverse_iterator<const_iterator></b> <span class=identifier>const_reverse_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>same as owning container </b><span class=identifier>node_type</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>following [container.insert.return] spec </b><span class=identifier>insert_return_type</span><span class=special>;</span>
|
||||
|
||||
<span class=comment>// construct/copy/destroy:</span>
|
||||
|
||||
@@ -275,11 +268,6 @@ indices, bearing in mind the occasional differences in complexity.
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>InputIterator</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>InputIterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>InputIterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>initializer_list</span><span class=special><</span><span class=identifier>value_type</span><span class=special>></span> <span class=identifier>list</span><span class=special>);</span>
|
||||
<span class=identifier>insert_return_type</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>node_type</span><span class=special>&&</span> <span class=identifier>nh</span><span class=special>);</span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>node_type</span><span class=special>&&</span> <span class=identifier>nh</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>node_type</span> <span class=identifier>extract</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
<span class=identifier>node_type</span> <span class=identifier>extract</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>key_type</span><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>iterator</span> <span class=identifier>erase</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
<span class=identifier>size_type</span> <span class=identifier>erase</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>key_type</span><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
@@ -297,16 +285,6 @@ indices, bearing in mind the occasional differences in complexity.
|
||||
<span class=keyword>void</span> <span class=identifier>swap</span><span class=special>(</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>clear</span><span class=special>()</span><span class=keyword>noexcept</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span> <span class=keyword>void</span> <span class=identifier>merge</span><span class=special>(</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>pair</span><span class=special><</span><span class=identifier>iterator</span><span class=special>,</span><span class=keyword>bool</span><span class=special>></span> <span class=identifier>merge</span><span class=special>(</span>
|
||||
<span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>i</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>merge</span><span class=special>(</span>
|
||||
<span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>first</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
|
||||
<span class=comment>// observers:</span>
|
||||
|
||||
<span class=identifier>key_from_value</span> <span class=identifier>key_extractor</span><span class=special>()</span><span class=keyword>const</span><span class=special>;</span>
|
||||
@@ -326,11 +304,6 @@ indices, bearing in mind the occasional differences in complexity.
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>CompatibleCompare</span><span class=special>></span>
|
||||
<span class=identifier>size_type</span> <span class=identifier>count</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>CompatibleCompare</span><span class=special>&</span> <span class=identifier>comp</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>></span>
|
||||
<span class=keyword>bool</span> <span class=identifier>contains</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>CompatibleCompare</span><span class=special>></span>
|
||||
<span class=keyword>bool</span> <span class=identifier>contains</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span><span class=keyword>const</span> <span class=identifier>CompatibleCompare</span><span class=special>&</span> <span class=identifier>comp</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>></span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>lower_bound</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>CompatibleKey</span><span class=special>&</span> <span class=identifier>x</span><span class=special>)</span><span class=keyword>const</span><span class=special>;</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>CompatibleKey</span><span class=special>,</span><span class=keyword>typename</span> <span class=identifier>CompatibleCompare</span><span class=special>></span>
|
||||
@@ -462,7 +435,8 @@ section</a>. The complexity signature of ranked indices is:
|
||||
<ul>
|
||||
<li>copying: <code>c(n)=n*log(n)</code>,</li>
|
||||
<li>insertion: <code>i(n)=log(n)</code>,</li>
|
||||
<li>hinted insertion: <b><code>h(n)=log(n)</code></b>,</li>
|
||||
<li>hinted insertion: <code>h(n)=1</code> (constant) if the hint element
|
||||
is immediately after the point of insertion, <code>h(n)=log(n)</code> otherwise,</li>
|
||||
<li>deletion: <b><code>d(n)=log(n)</code></b> ,</li>
|
||||
<li>replacement: <code>r(n)=1</code> (constant) if the element position does not
|
||||
change, <code>r(n)=log(n)</code> otherwise,</li>
|
||||
@@ -473,12 +447,12 @@ section</a>. The complexity signature of ranked indices is:
|
||||
<p>
|
||||
These complexity guarantees are the same as those of
|
||||
<a href="ord_indices.html#complexity_signature">ordered indices</a>
|
||||
except for hinted insertion and deletion, which are <code>log(n)</code> here and amortized constant there.
|
||||
except for deletion, which is <code>log(n)</code> here and amortized constant there.
|
||||
</p>
|
||||
|
||||
<h4><a name="instantiation_types">Instantiation types</a></h4>
|
||||
|
||||
<p>Ranked indices are instantiated internally to <code>multi_index_container</code> and
|
||||
<p>Ordered indices are instantiated internally to <code>multi_index_container</code> and
|
||||
specified by means of <a href="indices.html#indexed_by"><code>indexed_by</code></a>
|
||||
with <a href="#unique_non_unique"> index specifiers <code>ranked_unique</code>
|
||||
and <code>ranked_non_unique</code></a>. Instantiations are dependent on the
|
||||
@@ -494,47 +468,6 @@ These types are subject to the same requirements as specified for
|
||||
<a href="ord_indices.html#instantiation_types">ordered indices</a>.
|
||||
</p>
|
||||
|
||||
<h4><a name="types">Nested types</a></h4>
|
||||
|
||||
<code>iterator<br>
|
||||
const_iterator</code>
|
||||
|
||||
<blockquote>
|
||||
These types depend only on <code>node_type</code> and the position of
|
||||
the index in the <code>multi_index_container</code>.
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="set_operations">Set operations</a></h4>
|
||||
|
||||
<p>
|
||||
See the documentation of ordered indices for an explanation of the notions of
|
||||
<a href="ord_indices.html#set_operations"><i>compatible extension</i> and
|
||||
<i>compatible key</i></a>, which are referred to below.
|
||||
</p>
|
||||
|
||||
<a name="count">
|
||||
<code>template<typename CompatibleKey><br>
|
||||
size_type count(const CompatibleKey& x)const;
|
||||
</code></a>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>CompatibleKey</code> is a compatible key of
|
||||
<code>key_compare</code>.<br>
|
||||
<b>Effects:</b> Returns the number of elements with key equivalent to <code>x</code>.<br>
|
||||
<b>Complexity:</b> <code>O(log(n))</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>template<typename CompatibleKey,typename CompatibleCompare><br>
|
||||
size_type count(const CompatibleKey& x,const CompatibleCompare& comp)const;
|
||||
</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> (<code>CompatibleKey</code>, <code>CompatibleCompare</code>)
|
||||
is a compatible extension of <code>key_compare</code>.<br>
|
||||
<b>Effects:</b> Returns the number of elements with key equivalent to <code>x</code>.<br>
|
||||
<b>Complexity:</b> <code>O(log(n))</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="rank_operations">Rank operations</a></h4>
|
||||
|
||||
<p>
|
||||
@@ -699,9 +632,9 @@ Hashed indices
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised February 5th 2022</p>
|
||||
<p>Revised May 4th 2015</p>
|
||||
|
||||
<p>© Copyright 2003-2022 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2015 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+65
-188
@@ -40,7 +40,6 @@ Random access indices
|
||||
<ul>
|
||||
<li><a href="#complexity_signature">Complexity signature</a></li>
|
||||
<li><a href="#instantiation_types">Instantiation types</a></li>
|
||||
<li><a href="#types">Nested types</a></li>
|
||||
<li><a href="#constructors">Constructors, copy and assignment</a></li>
|
||||
<li><a href="#iterators">Iterators</a></li>
|
||||
<li><a href="#capacity">Capacity operations</a></li>
|
||||
@@ -153,12 +152,8 @@ like <code>std::list</code>. Elements in a sequenced index are by default
|
||||
sorted according to their order of insertion: this means that new elements
|
||||
inserted through a different index of the <code>multi_index_container</code> are appended
|
||||
to the end of the sequenced index. Additionally, the index allows for free
|
||||
reordering of elements in the same vein as <code>std::list</code> does.
|
||||
Iterators (including to the end of the index) and pointers and references to an element
|
||||
remain valid during the lifetime of the associated container (which can change
|
||||
upon swapping), or until the referred-to element is erased or extracted;
|
||||
pointers and references to an extracted element, but not so for iterators,
|
||||
become valid again once the element is re-inserted.
|
||||
reordering of elements in the same vein as <code>std::list</code> does. Validity
|
||||
of iterators and references to elements is preserved in all operations.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
@@ -177,7 +172,7 @@ most important differences are:
|
||||
<code>std::list</code>.
|
||||
</li>
|
||||
<li>Elements in a sequenced index are not mutable, and can only be changed
|
||||
in place by means of <a href="#replace"><code>replace</code></a> and
|
||||
by means of <a href="#replace"><code>replace</code></a> and
|
||||
<a href="#modify"><code>modify</code></a> member functions.
|
||||
</li>
|
||||
</ul>
|
||||
@@ -212,8 +207,6 @@ most important differences are:
|
||||
std::reverse_iterator<iterator></b> <span class=identifier>reverse_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>equivalent to
|
||||
std::reverse_iterator<const_iterator></b> <span class=identifier>const_reverse_iterator</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>same as owning container </b><span class=identifier>node_type</span><span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <b>following [container.insert.return] spec </b><span class=identifier>insert_return_type</span><span class=special>;</span>
|
||||
|
||||
<span class=comment>// construct/copy/destroy:</span>
|
||||
|
||||
@@ -281,9 +274,6 @@ most important differences are:
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>InputIterator</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>InputIterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>InputIterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>initializer_list</span><span class=special><</span><span class=identifier>value_type</span><span class=special>></span> <span class=identifier>list</span><span class=special>);</span>
|
||||
<span class=identifier>insert_return_type</span> <span class=identifier>insert</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>node_type</span><span class=special>&&</span> <span class=identifier>nh</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>node_type</span> <span class=identifier>extract</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
|
||||
<span class=identifier>iterator</span> <span class=identifier>erase</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>);</span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>erase</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
@@ -300,16 +290,10 @@ most important differences are:
|
||||
|
||||
<span class=comment>// list operations:</span>
|
||||
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span> <span class=keyword>void</span> <span class=identifier>splice</span><span class=special>(</span><span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>pair</span><span class=special><</span><span class=identifier>iterator</span><span class=special>,</span><span class=keyword>bool</span><span class=special>></span> <span class=identifier>splice</span><span class=special>(</span>
|
||||
<span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>i</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Index</span><span class=special>></span>
|
||||
<span class=keyword>void</span> <span class=identifier>splice</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>splice</span><span class=special>(</span><span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span><span class=identifier>iterator</span> <span class=identifier>i</span><span class=special>);</span>
|
||||
<span class=keyword>void</span> <span class=identifier>splice</span><span class=special>(</span>
|
||||
<span class=identifier>const_iterator</span> <span class=identifier>position</span><span class=special>,</span><span class=identifier>Index</span><span class=special>&&</span> <span class=identifier>x</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>first</span><span class=special>,</span>
|
||||
<span class=keyword>typename</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>remove_reference_t</span><span class=special><</span><span class=identifier>Index</span><span class=special>>::</span><span class=identifier>const_iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
<span class=identifier>iterator</span> <span class=identifier>position</span><span class=special>,</span><b>index class name</b><span class=special>&</span> <span class=identifier>x</span><span class=special>,</span><span class=identifier>iterator</span> <span class=identifier>first</span><span class=special>,</span><span class=identifier>iterator</span> <span class=identifier>last</span><span class=special>);</span>
|
||||
|
||||
<span class=keyword>void</span> <span class=identifier>remove</span><span class=special>(</span><span class=keyword>const</span> <span class=identifier>value_type</span><span class=special>&</span> <span class=identifier>value</span><span class=special>);</span>
|
||||
<span class=keyword>template</span><span class=special><</span><span class=keyword>typename</span> <span class=identifier>Predicate</span><span class=special>></span> <span class=keyword>void</span> <span class=identifier>remove_if</span><span class=special>(</span><span class=identifier>Predicate</span> <span class=identifier>pred</span><span class=special>);</span>
|
||||
@@ -427,16 +411,6 @@ index specifier. Instantiations are dependent on the following types:
|
||||
<a href="indices.html#tag"><code>tag</code></a>.
|
||||
</p>
|
||||
|
||||
<h4><a name="types">Nested types</a></h4>
|
||||
|
||||
<code>iterator<br>
|
||||
const_iterator</code>
|
||||
|
||||
<blockquote>
|
||||
These types depend only on <code>node_type</code> and the position of
|
||||
the index in the <code>multi_index_container</code>.
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="constructors">Constructors, copy and assignment</a></h4>
|
||||
|
||||
<p>
|
||||
@@ -525,7 +499,7 @@ into <code>multi_index_container</code>.<br>
|
||||
elements (first version) or copies of <code>x</code> (second version) at the end of
|
||||
the index. If <code>n<size()</code>, erases the last <code>size()-n</code> elements.<br>
|
||||
<b>Note:</b> If an expansion is requested, the size of the index is not guaranteed
|
||||
to be <code>n</code> after this operation (other indices may ban insertions).
|
||||
to be <code>n</code> after this operation (other indices may ban insertions.)
|
||||
</blockquote>
|
||||
|
||||
<h4><a name="modifiers">Modifiers</a></h4>
|
||||
@@ -670,40 +644,6 @@ number of elements in [<code>first</code>,<code>last</code>).<br>
|
||||
</pre></blockquote>
|
||||
</blockquote>
|
||||
|
||||
<code>insert_return_type insert(const_iterator position,node_type&& nh);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>nh.empty() || get_allocator()==nh.get_allocator()</code>.<br>
|
||||
<b>Effects:</b> Does nothing if <code>nh</code> is empty; otherwise,
|
||||
inserts the node owned by <code>nh</code> before <code>position</code> if insertion
|
||||
is allowed by all other indices of the <code>multi_index_container</code>.<br>
|
||||
<b>Postconditions:</b> <code>nh</code> is empty.<br>
|
||||
<b>Returns:</b> A value <code>p</code> of type <code>insert_return_type</code>.
|
||||
If <code>nh</code> is empty, <code>p.position</code> is <code>end()</code>,
|
||||
<code>p.inserted</code> is <code>false</code> and <code>p.node</code> is empty;
|
||||
on successful insertion, <code>p.position</code> points to the element inserted,
|
||||
<code>p.inserted</code> is <code>true</code> and <code>p.node</code>
|
||||
is empty;
|
||||
if the insertion failed, <code>p.position</code> points to an element that caused
|
||||
the insertion to be banned, <code>p.inserted</code> is <code>false</code> and
|
||||
<code>p.node</code> owns the original node.
|
||||
Note that more than one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> <code>O(I(n))</code>.<br>
|
||||
<b>Exception safety:</b> Strong. If an exception
|
||||
is thrown, <code>nh</code> is not changed.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>node_type extract(const_iterator position);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>position</code> is a valid dereferenceable iterator
|
||||
of the index.<br>
|
||||
<b>Effects:</b> Extracts the node of the element pointed to by <code>position</code>.<br>
|
||||
<b>Returns:</b> A node handle owning the extracted node.<br>
|
||||
<b>Complexity:</b> <code>O(D(n))</code>.<br>
|
||||
<b>Exception safety:</b> <code>nothrow</code>.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>iterator erase(iterator position);</code>
|
||||
|
||||
<blockquote>
|
||||
@@ -819,122 +759,62 @@ is rethrown.
|
||||
|
||||
<p>
|
||||
Sequenced indices provide the full set of list operations found in
|
||||
<code>std::list</code>, extended in some cases such as <code>splice</code>;
|
||||
the semantics of these member functions, however,
|
||||
typically differs from that of <code>std::list</code> as insertions
|
||||
may not succeed due to banning by other indices. Similarly, the complexity
|
||||
<code>std::list</code>; the semantics of these member functions, however,
|
||||
differ from that of <code>std::list</code> in some cases as insertions
|
||||
might not succeed due to banning by other indices. Similarly, the complexity
|
||||
of the operations may depend on the other indices belonging to the
|
||||
same <code>multi_index_container</code>.
|
||||
</p>
|
||||
|
||||
<a name="splice"><code>template<typename Index> void splice(const_iterator position,Index&& x);</code></a>
|
||||
<code>void splice(iterator position,<b>index class name</b>& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>.
|
||||
<code>position</code> is a valid iterator of the index, and must be exactly <code>end()</code>
|
||||
if the source and destination containers are the same.<br>
|
||||
<b>Effects:</b>
|
||||
<blockquote><pre>
|
||||
<span class=identifier>splice</span><span class=special>(</span><span class=identifier>position</span><span class=special>,</span><span class=identifier>x</span><span class=special>,</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>begin</span><span class=special>(),</span><span class=identifier>x</span><span class=special>.</span><span class=identifier>end</span><span class=special>());</span>
|
||||
</pre></blockquote>
|
||||
<b>Requires:</b> <code>position</code> is a valid iterator of the index.
|
||||
<code>&x!=this</code>.<br>
|
||||
<b>Effects:</b> Inserts the contents of <code>x</code> before <code>position</code>,
|
||||
in the same order as they were in <code>x</code>. Those elements successfully
|
||||
inserted are erased from <code>x</code>.<br>
|
||||
<b>Complexity:</b> <code>O(x.size()*I(n+x.size()) + x.size()*D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> Basic.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>
|
||||
template<typename Index> std::pair<iterator,bool> splice(<br>
|
||||
const_iterator position,Index&& x,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator i);
|
||||
</code>
|
||||
<code>void splice(iterator position,<b>index class name</b>& x,iterator i);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>.
|
||||
If <code>get_allocator()!=x.get_allocator()</code>,
|
||||
<code>value_type</code> must be <code>CopyInsertable</code> into the destination
|
||||
<code>multi_index_container</code>.
|
||||
<code>position</code> is a valid iterator of the index.
|
||||
<code>i</code> is a valid dereferenceable iterator of <code>x</code>.<br>
|
||||
<b>Effects:</b>
|
||||
<ul>
|
||||
<li><b>(Same container)</b> if the source and destination containers are the same, repositions
|
||||
the element pointed to by <code>i</code> before <code>position</code> unless both
|
||||
iterators refer to the same element.</li>
|
||||
<li><b>(Transfer splice)</b> else, if <code>get_allocator()==x.get_allocator()</code>,
|
||||
transfers the node of the element referred to by <code>i</code> into the
|
||||
destination <code>multi_index_container</code> right before <code>position</code>
|
||||
if insertion is allowed by all other indices of the <code>multi_index_container</code>.</li>
|
||||
<li><b>(Destructive splice)</b> else, insertion of <code>*i</code> is tried before
|
||||
<code>position</code>; if the operation is successful, the element is erased from <code>x</code>.
|
||||
</li>
|
||||
</ul>
|
||||
<b>Postconditions:</b> If transfer succeeds, for any index in the source container
|
||||
having the same <code>iterator</code>/<code>const_iterator</code> types as the corresponding
|
||||
index in the destination container, iterators referring to <code>*i</code>
|
||||
remain valid and behave as iterators of the destination index.<br>
|
||||
<b>Returns:</b> The return value is a pair <code>p</code>. <code>p.second</code>
|
||||
is <code>true</code> if and only if insertion (either through transfer or copy insertion)
|
||||
took place or the source and destination containers are the same.
|
||||
If <code>p.second</code> is <code>true</code>,
|
||||
<code>p.first</code> points to the inserted element or to <code>*i</code> if the
|
||||
source and destination containers are the same; otherwise, <code>p.first</code>
|
||||
points to an element that caused the insertion to be banned. Note that more than
|
||||
one element can be causing insertion not to be allowed.<br>
|
||||
<b>Complexity:</b> If the source and destination containers are the same,
|
||||
constant; otherwise, <code>O(I(n)+D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> If the source and destination containers are the same,
|
||||
<code>nothrow</code>; otherwise strong.<br>
|
||||
<b>Implementation note:</b> The destructive variant of this operation is provided
|
||||
for reasons of backwards compatibility with previous versions of this library where
|
||||
allocator equality was not required.
|
||||
<b>Requires:</b> <code>position</code> is a valid iterator of the index.
|
||||
<code>i</code> is a valid dereferenceable iterator <code>x</code>.<br>
|
||||
<b>Effects:</b> Inserts the element pointed to by <code>i</code> before
|
||||
<code>position</code>: if insertion is successful, the element is erased from
|
||||
<code>x</code>. In the special case <code>&x==this</code>, no copy or
|
||||
deletion is performed, and the operation is always successful. If
|
||||
<code>position==i</code>, no operation is performed.<br>
|
||||
<b>Postconditions:</b> If <code>&x==this</code>, no iterator or reference
|
||||
is invalidated.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, constant; otherwise
|
||||
<code>O(I(n) + D(n))</code>.<br>
|
||||
<b>Exception safety:</b> If <code>&x==this</code>, <code>nothrow</code>;
|
||||
otherwise, strong.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>
|
||||
template<typename Index> void splice(<br>
|
||||
const_iterator position,Index&& x,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator first,<br>
|
||||
typename std::remove_reference_t<Index>::const_iterator last);
|
||||
</code>
|
||||
<code>void splice(iterator position,<b>index class name&</b> x,iterator first,iterator last);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b> <code>x</code> is a non-const reference to an index of a
|
||||
<a href="multi_index_container.html#node_type">node-compatible</a>
|
||||
<code>multi_index_container</code>.
|
||||
If <code>get_allocator()!=x.get_allocator()</code>,
|
||||
<code>value_type</code> must be <code>CopyInsertable</code> into the destination
|
||||
<code>multi_index_container</code>.
|
||||
<code>position</code> is a valid iterator of the index and does not point to any element in
|
||||
[<code>first</code>,<code>last</code>).
|
||||
[<code>first</code>,<code>last</code>) is a valid range of <code>x</code>.<br>
|
||||
<b>Effects:</b>
|
||||
<ul>
|
||||
<li><b>(Same container)</b> if the source and destination containers are the same, repositions all the elements
|
||||
of [<code>first</code>,<code>last</code>), in this order, before <code>position</code>.
|
||||
</li>
|
||||
<li><b>(Transfer splice)</b> else, if <code>get_allocator()==x.get_allocator()</code>, then, for each node in
|
||||
[<code>first</code>,<code>last</code>), in this order, the node is transferred to the
|
||||
<code>multi_index_container</code> right before <code>position</code>
|
||||
if insertion is allowed by all other indices of the
|
||||
<code>multi_index_container</code>.</li>
|
||||
<li><b>(Destructive splice)</b> else, for each element in [<code>first</code>,<code>last</code>), in this order,
|
||||
insertion is tried before <code>position</code>; if the operation is successful, the
|
||||
element is erased from <code>x</code>.
|
||||
</li>
|
||||
</ul>
|
||||
<b>Postconditions:</b> For any index in the source container having the same
|
||||
<code>iterator</code>/<code>const_iterator</code> types as the corresponding
|
||||
index in the destination container, iterators referring to the transferred elements
|
||||
remain valid and behave as iterators of the destination index.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, constant; else, if
|
||||
the source and destination containers are the same, <code>O(m)</code>;
|
||||
otherwise, <code>O(m*(I(n+m)+D(x.size())))</code>, where
|
||||
<code>m</code> is the number of elements in [<code>first</code>,<code>last</code>).<br>
|
||||
<b>Exception safety:</b> If the source and destination containers are the same,
|
||||
<code>nothrow</code>; otherwise basic.<br>
|
||||
<b>Implementation note:</b> The destructive variant of this operation is provided
|
||||
for reasons of backwards compatibility with previous versions of this library where
|
||||
allocator equality was not required.
|
||||
<b>Requires:</b> <code>position</code> is a valid iterator of the index.
|
||||
<code>first</code> and <code>last</code> are valid iterators of <code>x</code>.
|
||||
<code>last</code> is reachable from <code>first</code>. <code>position</code>
|
||||
is not in the range [<code>first</code>,<code>last</code>).<br>
|
||||
<b>Effects:</b> For each element in the range [<code>first</code>,<code>last</code>),
|
||||
insertion is tried before <code>position</code>; if the operation is successful,
|
||||
the element is erased from <code>x</code>. In the special case
|
||||
<code>&x==this</code>, no copy or deletion is performed, and insertions are
|
||||
always successful.<br>
|
||||
<b>Postconditions:</b> If <code>&x==this</code>, no iterator or reference
|
||||
is invalidated.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, constant; otherwise
|
||||
<code>O(m*I(n+m) + m*D(x.size()))</code> where <code>m</code> is the number
|
||||
of elements in [<code>first</code>,<code>last</code>).<br>
|
||||
<b>Exception safety:</b> If <code>&x==this</code>, <code>nothrow</code>;
|
||||
otherwise, basic.<br>
|
||||
</blockquote>
|
||||
|
||||
<code>void remove(const value_type& value);</code>
|
||||
@@ -983,22 +863,20 @@ is the number of elements erased.<br>
|
||||
<code>void merge(index class name& x);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b>
|
||||
Either <code>get_allocator()==x.get_allocator()</code> or <code>value_type</code>
|
||||
is <code>CopyInsertable</code> into the <code>multi_index_container</code>.
|
||||
<code>std::less<value_type></code> induces a
|
||||
<b>Requires:</b> <code>std::less<value_type></code> induces a
|
||||
strict weak ordering over <code>value_type</code>.
|
||||
Both the index and <code>x</code> are sorted according to
|
||||
<code>std::less<value_type></code>.<br>
|
||||
<b>Effects:</b> Attempts to splice every element of <code>x</code> into the
|
||||
corresponding position of the index (according to the order). The resulting sequence
|
||||
<b>Effects:</b> Attempts to insert every element of <code>x</code> into the
|
||||
corresponding position of the index (according to the order). Elements
|
||||
successfully inserted are erased from <code>x</code>. The resulting sequence
|
||||
is stable, i.e. equivalent elements of either container preserve their
|
||||
relative position. In the special case <code>&x==this</code>, no operation
|
||||
is performed.<br>
|
||||
<b>Postconditions:</b> Elements in the index and remaining elements in
|
||||
<code>x</code> are sorted.
|
||||
Validity of iterators and references is preserved, except to elements removed
|
||||
from <code>x</code> if <code>get_allocator()!=x.get_allocator()</code>.<br>
|
||||
Validity of iterators to the index and of non-erased elements of <code>x</code>
|
||||
references is preserved.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, constant; otherwise
|
||||
<code>O(n + x.size()*I(n+x.size()) + x.size()*D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> If <code>&x==this</code>, <code>nothrow</code>;
|
||||
@@ -1008,20 +886,19 @@ otherwise, basic.<br>
|
||||
<code>template <typename Compare> void merge(index class name& x,Compare comp);</code>
|
||||
|
||||
<blockquote>
|
||||
<b>Requires:</b>
|
||||
Either <code>get_allocator()==x.get_allocator()</code> or <code>value_type</code>
|
||||
is <code>CopyInsertable</code> into the <code>multi_index_container</code>.
|
||||
<code>Compare</code> induces a strict weak ordering over <code>value_type</code>.
|
||||
<b>Requires:</b> <code>Compare</code> induces a
|
||||
strict weak ordering over <code>value_type</code>.
|
||||
Both the index and <code>x</code> are sorted according to <code>comp</code>.<br>
|
||||
<b>Effects:</b> Attempts to splice every element of <code>x</code> into the
|
||||
corresponding position of the index (according to <code>comp</code>). The resulting
|
||||
<b>Effects:</b> Attempts to insert every element of <code>x</code> into the
|
||||
corresponding position of the index (according to <code>comp</code>).
|
||||
Elements successfully inserted are erased from <code>x</code>. The resulting
|
||||
sequence is stable, i.e. equivalent elements of either container preserve
|
||||
their relative position. In the special case <code>&x==this</code>, no
|
||||
operation is performed.<br>
|
||||
<b>Postconditions:</b> Elements in the index and remaining elements in
|
||||
<code>x</code> are sorted according to <code>comp</code>.
|
||||
Validity of iterators and references is preserved, except to elements removed
|
||||
from <code>x</code> if <code>get_allocator()!=x.get_allocator()</code>.<br>
|
||||
Validity of iterators to the index and of non-erased elements of <code>x</code>
|
||||
references is preserved.<br>
|
||||
<b>Complexity:</b> If <code>&x==this</code>, constant; otherwise
|
||||
<code>O(n + x.size()*I(n+x.size()) + x.size()*D(x.size()))</code>.<br>
|
||||
<b>Exception safety:</b> If <code>&x==this</code>, <code>nothrow</code>;
|
||||
@@ -1158,7 +1035,7 @@ Operation: loading of an <code>iterator</code> or <code>const_iterator</code>
|
||||
then <code>*it'</code> is the restored copy of <code>*it</code>, otherwise
|
||||
<code>it'==end()</code>.<br>
|
||||
<b>Note:</b> It is allowed that <code>it</code> be a <code>const_iterator</code>
|
||||
and the restored <code>it'</code> an <code>iterator</code>, or vice versa.
|
||||
and the restored <code>it'</code> an <code>iterator</code>, or viceversa.
|
||||
</blockquote>
|
||||
|
||||
<hr>
|
||||
@@ -1175,9 +1052,9 @@ Random access indices
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised August 30th 2021</p>
|
||||
<p>Revised December 29th 2018</p>
|
||||
|
||||
<p>© Copyright 2003-2021 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2018 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+5
-233
@@ -30,19 +30,6 @@ Acknowledgements
|
||||
<h2>Contents</h2>
|
||||
|
||||
<ul>
|
||||
<li><a href="#boost_1_92">Boost 1.92 release</a></li>
|
||||
<li><a href="#boost_1_91">Boost 1.91 release</a></li>
|
||||
<li><a href="#boost_1_85">Boost 1.85 release</a></li>
|
||||
<li><a href="#boost_1_84">Boost 1.84 release</a></li>
|
||||
<li><a href="#boost_1_83">Boost 1.83 release</a></li>
|
||||
<li><a href="#boost_1_82">Boost 1.82 release</a></li>
|
||||
<li><a href="#boost_1_81">Boost 1.81 release</a></li>
|
||||
<li><a href="#boost_1_80">Boost 1.80 release</a></li>
|
||||
<li><a href="#boost_1_79">Boost 1.79 release</a></li>
|
||||
<li><a href="#boost_1_78">Boost 1.78 release</a></li>
|
||||
<li><a href="#boost_1_77">Boost 1.77 release</a></li>
|
||||
<li><a href="#boost_1_74">Boost 1.74 release</a></li>
|
||||
<li><a href="#boost_1_73">Boost 1.73 release</a></li>
|
||||
<li><a href="#boost_1_71">Boost 1.71 release</a></li>
|
||||
<li><a href="#boost_1_70">Boost 1.70 release</a></li>
|
||||
<li><a href="#boost_1_69">Boost 1.69 release</a></li>
|
||||
@@ -74,222 +61,6 @@ Acknowledgements
|
||||
<li><a href="#boost_1_33">Boost 1.33 release</a></li>
|
||||
</ul>
|
||||
|
||||
<h2><a name="boost_1_92">Boost 1.92 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Fancy pointer support has been extended so that <code>multi_index_container</code>
|
||||
iterators now store references to the elements through the allocator's pointer type.
|
||||
In particular, this means that iterators can now be placed in shared memory using
|
||||
<a href="../../interprocess/index.html">Boost.Interprocess</a> allocators.
|
||||
</li>
|
||||
<li>Fixed a performance issue with hashed indices when rehashing at very large
|
||||
container sizes (<a href="https://github.com/boostorg/multi_index/pull/94">PR#94</a>).
|
||||
Contributed by Daniel Král.
|
||||
</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_91">Boost 1.91 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li><b>Breaking change:</b> All type lists accepted or provided by the library (<code>indexed_by</code>,
|
||||
<code>tag</code>, nested typedefs <code>index_specifier_type_list</code>,
|
||||
<code>index_type_list</code>, <code>iterator_type_list</code> and
|
||||
<code>const_iterator_type_list</code>) are no longer based on
|
||||
<a href="../../mpl">Boost.MPL</a> but instead they are now
|
||||
<a href="../../mp11/doc/html/mp11.html#definitions">Boost.Mp11 lists</a>.
|
||||
As a result, Boost.MultiIndex doesn't depend anymore on Boost.MPL.
|
||||
It is expected that most user code won't be impacted by this
|
||||
change, but the previous behavior may be restored, however, by
|
||||
globally defining the macro
|
||||
<code>BOOST_MULTI_INDEX_ENABLE_MPL_SUPPORT</code>.
|
||||
Legacy support for Boost.MPL may be eventually deprecated and removed in the future.
|
||||
</li>
|
||||
<li><b>Breaking change:</b> <code>composite_key</code> and associated
|
||||
class templates (<code>composite_key_equal_to</code>, <code>composite_key_compare</code>,
|
||||
<code>composite_key_hash</code>) have been made variadic (previously the maximum
|
||||
number of template arguments was limited by <code>BOOST_MULTI_INDEX_LIMIT_COMPOSITE_KEY_SIZE</code>).
|
||||
This change should be transparent to users, with the exception that
|
||||
<code>composite_key::key_extractors</code> returns a <code>std::tuple</code>
|
||||
instead of a <code>boost::tuple</code> (and similarly for the rest of affected
|
||||
class templates).
|
||||
</li>
|
||||
<li>Removed internal workarounds and fallbacks to support pre-C++11 compilers.
|
||||
</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_85">Boost 1.85 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Fixed documentation errors.</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_84">Boost 1.84 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Fixed a serialization-related compile-time bug in old compilers
|
||||
without ADL support
|
||||
(<a href="https://github.com/boostorg/multi_index/issues/70">issue #70</a>).
|
||||
</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
|
||||
<h2><a name="boost_1_83">Boost 1.83 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Updated range <code>insert</code> in non-unique ordered indices to preserve insertion order
|
||||
of equivalent elements
|
||||
(<a href="https://github.com/boostorg/multi_index/issues/68">issue #68</a>).
|
||||
</li>
|
||||
<li>Serialization now uses <code>std::size_t</code> instead of <code>unsigned long</code>
|
||||
to save and load the size of a <code>multi_index_container</code>
|
||||
(<code>unsigned long</code> is smaller than <code>std::size_t</code> in LLP64 data models).
|
||||
<code>multi_index_container</code> serialization
|
||||
<a href="../../serialization/doc/tutorial.html#versioning">class version</a> has been
|
||||
bumped from 3 to 4 to reflect this change.
|
||||
</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_82">Boost 1.82 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Serialization now uses <code>unsigned long</code> instead of
|
||||
<a href="../../serialization/doc/wrappers.html#collection_size_type"><code>collection_size_type</code></a>,
|
||||
and <code>multi_index_container</code> serialization
|
||||
<a href="../../serialization/doc/tutorial.html#versioning">class version</a> has been
|
||||
bumped from 2 to 3 to reflect this change.
|
||||
Reading old archives may fail for custom archive types giving special treatment to
|
||||
<code>collection_size_type</code> values: if this is the case, globally define
|
||||
the macro <code>BOOST_MULTI_INDEX_ENABLE_SERIALIZATION_COMPATIBILITY_V2</code>
|
||||
to ensure backwards compatibility in reading operations.
|
||||
</li>
|
||||
<li>Maintenance work.</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_81">Boost 1.81 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Maintenance work.</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_80">Boost 1.80 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Maintenance work.</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_79">Boost 1.79 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Improved the efficiency of <code>count</code> operations in ranked indices from
|
||||
<code>O(log(n) + count)</code> to <code>O(log(n))</code>.
|
||||
Contributed by Damian Sawicki.
|
||||
</li>
|
||||
<li>Maintenance work.</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_78">Boost 1.78 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Added <code>contains</code> to key-based indices
|
||||
(<a href="https://github.com/boostorg/multi_index/issues/35">issue #35</a>).
|
||||
</li>
|
||||
<li>Added <code>merge</code> operations to key-based indices. The functionality goes beyond
|
||||
the standard specification for (unordered) associative containers in a number of ways,
|
||||
most notably:
|
||||
<ul>
|
||||
<li>The source index can be of any type, including non key-based indices.</li>
|
||||
<li>Partial merge is provided: for instance, <code>x.merge(y,first,last)</code>
|
||||
merges only the elements of <code>y</code> within [<code>first</code>,<code>last</code>).
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>Previous versions of <code>splice</code> for sequenced and random access indices
|
||||
were destructive, i.e. elements were copy-inserted into the destination and then erased
|
||||
from the source. Now, <code>splice</code> is based on node transfer much as <code>merge</code>
|
||||
in key-based indices, and has been similarly extended to accept source indices of any type:
|
||||
in fact, <code>splice</code> can be regarded as a frontend to the same functionality
|
||||
provided by <code>merge</code> in key-based indices. For reasons of backwards compatibility,
|
||||
the destructive behavior of <code>splice</code> has been retained in the case that the
|
||||
source and destination containers have unequal allocators.
|
||||
</li>
|
||||
<li>The fact has been documented that index iterator types do only depend on <code>node_type</code>
|
||||
and the position of the index in its <code>multi_index_container</code>,
|
||||
(except for hashed indices, where uniqueness/non-uniqueness is also a dependency). This has
|
||||
implications on the validity of iterators to elements transferred by <code>merge</code> or
|
||||
<code>splice</code>. This property is a variant of what has been called
|
||||
<a href="https://wg21.link/n2980">SCARY iterators</a> in the C++ standard mailing lists.
|
||||
SCARYness is currently (August 2021) not mandated for standard containers.
|
||||
</li>
|
||||
<li>Iterator SCARYness is now also preserved in <a href="tutorial/debug.html#safe_mode">safe mode</a>.
|
||||
</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_77">Boost 1.77 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>Maintenance work.</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_74">Boost 1.74 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li>
|
||||
Added <a href="tutorial/indices.html#node_handling">node extraction and insertion</a>
|
||||
following the analogous interface of associative containers as introduced in C++17.
|
||||
This feature has also been extended to non key-based indices, in contrast to C++
|
||||
standard library sequence containers, which do not provide such functionality.
|
||||
</li>
|
||||
<li>Clarified documentation on read/write key extractors
|
||||
(<a href="https://github.com/boostorg/multi_index/issues/32">issue #32</a>).
|
||||
</li>
|
||||
<li>Maintenance work.</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_73">Boost 1.73 release</a></h2>
|
||||
|
||||
<p>
|
||||
<ul>
|
||||
<li><code>multi_index_container</code> is now
|
||||
<a href="https://en.cppreference.com/w/cpp/named_req/AllocatorAwareContainer"><code>AllocatorAware</code></a>.
|
||||
</li>
|
||||
<li>Swapping of internal <code>KeyFromValue</code>, <code>Compare</code>, <code>Hash</code>
|
||||
and <code>Pred</code> objects now selects the appropriate <code>swap</code>
|
||||
function between <code>std::swap</code> and ADL candidates,
|
||||
in accordance with standard specifications in <b>[swappable.requirements]</b>
|
||||
(<a href="https://github.com/boostorg/multi_index/issues/29">issue #29</a>).
|
||||
</li>
|
||||
<li>Provided some internal copy constructors and assignment operators whose default
|
||||
implicit definition is deprecated in C++11 onwards (<b>[depr.impldec]</b>), which
|
||||
was warned about on some compilers.
|
||||
</li>
|
||||
<li>Maintenance work.</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="boost_1_71">Boost 1.71 release</a></h2>
|
||||
|
||||
<p>
|
||||
@@ -523,7 +294,7 @@ Acknowledgements
|
||||
</li>
|
||||
<li>Random access indices provide <code>shrink_to_fit()</code>.</li>
|
||||
</ul>
|
||||
Refer to the compiler specifics section for limitations
|
||||
Refer to the <a href="compiler_specifics.html">compiler specifics</a> section for limitations
|
||||
on pre-C++11 compilers.
|
||||
</li>
|
||||
<li>The following classes are deprecated:
|
||||
@@ -842,7 +613,8 @@ Acknowledgements
|
||||
Boost 1.32 release. This results in much shorter and more readable error
|
||||
messages and has also a beneficial impact on compilers with strict limits on
|
||||
symbol name lengths. Additionally, a section on further
|
||||
reduction of symbol name lengths has been added.
|
||||
<a href="compiler_specifics.html#symbol_reduction">reduction of symbol name
|
||||
lengths</a> has been added.
|
||||
</li>
|
||||
<li>Restructured some parts of the documentation, new examples.</li>
|
||||
<li>Maintenance fixes.</li>
|
||||
@@ -863,9 +635,9 @@ Acknowledgements
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised June 27th 2026</p>
|
||||
<p>Revised June 9th 2019</p>
|
||||
|
||||
<p>© Copyright 2003-2026 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2019 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2004 Joaquín M López Muñoz.
|
||||
/* Copyright 2003-2004 Joaqu匤 M L�ez Mu�z.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
|
||||
+17
-26
@@ -43,69 +43,60 @@ with some of the least common features offered by Boost.MultiIndex.
|
||||
<th>Description</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><a href="../test/test_alloc_awareness.cpp"><code>test_alloc_awareness.cpp</code></a></td>
|
||||
<td>Checks <a href="https://en.cppreference.com/w/cpp/named_req/AllocatorAwareContainer">allocator
|
||||
awareness</a>.</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_basic.cpp"><code>test_basic.cpp</code></a></td>
|
||||
<td>Simple program along the lines of the employees example studied in the
|
||||
tutorial.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_capacity.cpp"><code>test_capacity.cpp</code></a></td>
|
||||
<td><code>empty</code>, <code>size</code>, <code>resize</code>
|
||||
(non-key-based indices) and <code>reserve</code>/<code>capacity</code>
|
||||
(non key-based indices) and <code>reserve</code>/<code>capacity</code>
|
||||
(random access indices only).</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<tr>
|
||||
<td><a href="../test/test_comparison.cpp"><code>test_comparison.cpp</code></a></td>
|
||||
<td>Comparison between indices.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_composite_key.cpp"><code>test_composite_key.cpp</code></a></td>
|
||||
<td><code>composite_key</code> and <code>composite_key_compare</code>.</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<tr>
|
||||
<td><a href="../test/test_conv_iterators.cpp"><code>test_conv_iterators.cpp</code></a></td>
|
||||
<td>Checks convertibility of non-constant to constant iterators.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_copy_assignment.cpp"><code>test_copy_assignment.cpp</code></a></td>
|
||||
<td>Various forms of assignment: copy, <code>operator =</code>, insertion,
|
||||
(non key-based indices only) <code>assign</code>.
|
||||
(non key-based indices only) <code>assign</code> .
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<tr>
|
||||
<td><a href="../test/test_hash_ops.cpp"><code>test_hash_ops.cpp</code></a></td>
|
||||
<td>Hashing operations.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_iterators.cpp"><code>test_iterators.cpp</code></a></td>
|
||||
<td>Constant and non-constant iterators and their reverse variants.</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<tr>
|
||||
<td><a href="../test/test_key.cpp"><code>test_key.cpp</code></a></td>
|
||||
<td>Terse key specification syntax.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_key_extractors.cpp"><code>test_key_extractors.cpp</code></a></td>
|
||||
<td>Covers all use cases of key extractors shipped with the library.</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<tr>
|
||||
<td><a href="../test/test_list_ops.cpp"><code>test_list_ops.cpp</code></a></td>
|
||||
<td>List-like operations particular to sequenced and random access indices.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_modifiers.cpp"><code>test_modifiers.cpp</code></a></td>
|
||||
<td>Checks the family of insertion and erasing operations.</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_mpl_ops.cpp"><code>test_mpl_ops.cpp</code></a></td>
|
||||
<td>Boost.MPL interoperability (when <code> BOOST_MULTI_INDEX_ENABLE_MPL_SUPPORT</code> is enabled).</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><a href="../test/test_node_handling.cpp"><code>test_node_handling.cpp</code></a></td>
|
||||
<td>Operations involving node extraction and insertion.</td>
|
||||
<td><a href="../test/test_mpl_ops.cpp"><code>test_mpl_ops.cpp</code></a></td>
|
||||
<td>Metaprogramming manipulations of <code>multi_index_container</code> types.</td>
|
||||
</tr>
|
||||
<tr class="odd_tr">
|
||||
<td><a href="../test/test_observers.cpp"><code>test_observers.cpp</code></a></td>
|
||||
@@ -166,9 +157,9 @@ Future work
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised October 26th 2025</p>
|
||||
<p>Revised August 17th 2018</p>
|
||||
|
||||
<p>© Copyright 2003-2025 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2018 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+10
-10
@@ -114,7 +114,7 @@ construct easily becomes unmaintainable.
|
||||
<p>
|
||||
Boost.MultiIndex features <a href="#ord_indices"><i>ordered indices</i></a>, which
|
||||
sort the elements according to a particular key, and are designed to help programmers
|
||||
in need of sequences of elements for which <i>more than one</i> sorting criterion is
|
||||
in need of sequences of elements for which <i>more than one</i> sorting criteria are
|
||||
relevant. We do so by defining a <code>multi_index_container</code>
|
||||
instantiation composed of several ordered indices: each index, viewed in isolation,
|
||||
behaves much as an ordered <code>std::set</code> (or <code>std::multiset</code>), whilst
|
||||
@@ -268,7 +268,7 @@ does not show any advantage. The code for inserting the text into the container
|
||||
does not change as sequenced indices provide an interface similar to that of
|
||||
<code>std::list</code> (no explicit access to this index through
|
||||
<code>get<0>()</code> is needed as <code>multi_index_container</code> inherits the
|
||||
functionality of index #0). But the specification of an additional ordered index
|
||||
functionality of index #0.) But the specification of an additional ordered index
|
||||
allows us to implement <code>occurrences</code> and <code>delete_word</code>
|
||||
in a much more efficient manner:
|
||||
</p>
|
||||
@@ -417,7 +417,7 @@ for instance,
|
||||
<li><code>employee_set::nth_index<1>::type</code> is the type of
|
||||
index #1,</li>
|
||||
<li><code>employee_set::index<name>::type</code> is the type of the index
|
||||
tagged with <code>name</code> (the same index #1 in this case).</li>
|
||||
tagged with <code>name</code> (the same index #1 in this case.)</li>
|
||||
</ul>
|
||||
<code>get()</code>, on the other hand, is overloaded to serve both styles of access:
|
||||
</p>
|
||||
@@ -453,7 +453,7 @@ in the previous example can be rewritten to hold two different tags
|
||||
|
||||
<p>
|
||||
Each index of a <code>multi_index_container</code> uses its own
|
||||
iterator types, which are different from those of other indices. As is
|
||||
iterator types, which are different from those of another indices. As is
|
||||
the rule with STL containers, these iterators are defined as nested
|
||||
types of the index:
|
||||
</p>
|
||||
@@ -496,7 +496,7 @@ Currently, Boost.MultiIndex provides the following index types:
|
||||
<li>Ordered indices sort the elements like <code>std::set</code>s do and
|
||||
provide a similar interface. There are <i>unique</i> and <i>non-unique</i>
|
||||
variants: the former do not allow for duplicates, while the latter permit
|
||||
them (like <code>std::multiset</code>).</li>
|
||||
them (like <code>std::multiset</code>.)</li>
|
||||
<li>Ranked indices are a variation of ordered indices providing extra capabilities
|
||||
for querying and accessing elements based on their <i>rank</i> (the numerical position
|
||||
they occupy in the index).
|
||||
@@ -766,7 +766,7 @@ Here we are not only passing IDs instead of <code>employee</code> objects:
|
||||
an alternative comparison predicate is passed as well. In general, lookup operations
|
||||
of ordered indices are overloaded to accept
|
||||
<a href="../reference/ord_indices.html#set_operations"><i>compatible sorting
|
||||
criteria</i></a>. The somewhat cumbersome definition of compatibility in this context
|
||||
criteria</i></a>. The somewhat cumbersone definition of compatibility in this context
|
||||
is given in the reference, but roughly speaking we say that a comparison predicate
|
||||
<code>C1</code> is compatible with <code>C2</code> if any sequence sorted by
|
||||
<code>C2</code> is also sorted with respect to <code>C1</code>.
|
||||
@@ -801,7 +801,7 @@ The following shows a more interesting use of compatible predicates:
|
||||
Range searching, i.e. the lookup of all elements in a given interval, is a very
|
||||
frequent operation for which standard <code>lower_bound</code> and
|
||||
<code>upper_bound</code> can be resorted to, though in a cumbersome manner.
|
||||
For instance, the following code retrieves the elements of a
|
||||
For instance, the following code retrieves the elements of an
|
||||
<code>multi_index_container<double></code> in the interval [100,200]:
|
||||
</p>
|
||||
|
||||
@@ -1229,7 +1229,7 @@ Appropriate instantiations of <code>multi_index_container</code> can in fact sim
|
||||
<code>std::set</code>, <code>std::multiset</code> and (with more limitations)
|
||||
<code>std::list</code>, as shown in the
|
||||
<a href="techniques.html#emulate_std_containers">techniques</a>
|
||||
section. These simulations are nearly as efficient as the original STL
|
||||
section. These simulations are as nearly as efficient as the original STL
|
||||
containers; consult the <a href="../reference/index.html">reference</a> for further
|
||||
information on complexity guarantees and the
|
||||
<a href="../performance.html">performance section</a> for practical measurements of
|
||||
@@ -1250,9 +1250,9 @@ Index types
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised August 16th 2021</p>
|
||||
<p>Revised February 20th 2019</p>
|
||||
|
||||
<p>© Copyright 2003-2021 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2019 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
@@ -201,7 +201,7 @@ than strictly required by the C++ standard, as explained in detail in the
|
||||
An important type of non-standard allocators supported are those provided by the
|
||||
<a href="../../../interprocess/index.html">Boost Interprocess Library</a>;
|
||||
this opens up the possibility of placing <code>multi_index_container</code>s
|
||||
and their iterators in shared memory.
|
||||
in shared memory.
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
@@ -340,9 +340,9 @@ Debugging support
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised June 27th 2026</p>
|
||||
<p>Revised July 17th 2007</p>
|
||||
|
||||
<p>© Copyright 2003-2026 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2007 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+4
-26
@@ -34,7 +34,6 @@ Techniques
|
||||
<li><a href="#safe_mode">Safe mode</a>
|
||||
<ul>
|
||||
<li><a href="#serialization_and_safe_mode">Serialization and safe mode</a></li>
|
||||
<li><a href="#shared_memory_and_safe_mode">Containers placed in shared memory</a></li>
|
||||
</ul>
|
||||
</li>
|
||||
<li><a href="#invariant_check">Invariant-checking mode</a></li>
|
||||
@@ -126,8 +125,7 @@ is one value of the <code>safe_mode::error_code</code> enumeration:
|
||||
<span class=identifier>invalid_range</span><span class=special>,</span> <span class=comment>// last not reachable from first</span>
|
||||
<span class=identifier>inside_range</span><span class=special>,</span> <span class=comment>// iterator lies within a range (and it mustn't)</span>
|
||||
<span class=identifier>out_of_bounds</span><span class=special>,</span> <span class=comment>// move attempted beyond container limits</span>
|
||||
<span class=identifier>same_container</span><span class=special>,</span> <span class=comment>// containers ought to be different</span>
|
||||
<span class=identifier>unequal_allocators</span> <span class=comment>// allocators ought to be equal</span>
|
||||
<span class=identifier>same_container</span> <span class=comment>// containers ought to be different</span>
|
||||
<span class=special>};</span>
|
||||
|
||||
<span class=special>}</span> <span class=comment>// namespace multi_index::safe_mode</span>
|
||||
@@ -163,7 +161,7 @@ asserting:
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
Other possibilities, like outputting to a log or firing some kind of alert, are
|
||||
Other possibilites, like outputting to a log or firing some kind of alert, are
|
||||
also implementable.
|
||||
</p>
|
||||
|
||||
@@ -200,26 +198,6 @@ checked value by using the following workaround:
|
||||
<span class=identifier>it</span><span class=special>=</span><span class=identifier>es</span><span class=special>.</span><span class=identifier>project</span><span class=special><</span><span class=number>1</span><span class=special>>(</span><span class=identifier>it</span><span class=special>);</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<h3><a name="shared_memory_and_safe_mode">Containers placed in shared memory</a></h3>
|
||||
|
||||
<p>
|
||||
In general, safe mode <b>can't be used</b> when placing <code>multi_index_container</code>s
|
||||
in shared memory for interprocess communication
|
||||
(as in <a href="../examples.html#example12">this example</a>).
|
||||
There are some fundamental reasons for this limitation:
|
||||
<ul>
|
||||
<li>
|
||||
Operations from one process may invalidate or change ownership for iterators
|
||||
living in non-shared memory within another process: safe-mode machinery can't
|
||||
access those for bookkeeping.
|
||||
</li>
|
||||
<li>
|
||||
Safe mode uses internal mutexes not suitable for interprocess
|
||||
synchronization or persistence to a memory-mapped file.
|
||||
</li>
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="invariant_check">Invariant-checking mode</a></h2>
|
||||
|
||||
<p>
|
||||
@@ -261,9 +239,9 @@ Techniques
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised June 27th 2026</p>
|
||||
<p>Revised July 07th 2017</p>
|
||||
|
||||
<p>© Copyright 2003-2026 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2017 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
@@ -101,7 +101,7 @@ indices are met.
|
||||
|
||||
<p>
|
||||
All the public types of Boost.MultiIndex reside in namespace <code>::boost::multi_index</code>.
|
||||
Additionally, the main class template <code>multi_index_container</code> and global functions
|
||||
Additionaly, the main class template <code>multi_index_container</code> and global functions
|
||||
<code>get</code> and <code>project</code> are lifted to namespace <code>::boost</code>
|
||||
by means of <code>using</code> declarations. For brevity of exposition, the fragments
|
||||
of code in the documentation are written as if the following declarations were in effect:
|
||||
|
||||
+5
-113
@@ -55,7 +55,6 @@ Key extraction
|
||||
</li>
|
||||
<li><a href="#rearrange">Index rearranging</a></li>
|
||||
<li><a href="#iterator_to"><code>iterator_to</code></a></li>
|
||||
<li><a href="#node_handling">Node handling operations</a></li>
|
||||
<li><a href="#ordered_node_compression">Ordered indices node compression</a></li>
|
||||
</ul>
|
||||
|
||||
@@ -283,7 +282,7 @@ determining whether a hashed index is preferred over an ordered one.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
Hashed indices replicate the interface of <code>std::unordered_set</code> and
|
||||
Hashed indices replicate the interface as <code>std::unordered_set</code> and
|
||||
<code>std::unordered_multiset</code>, with only minor differences where required
|
||||
by the general constraints of <code>multi_index_container</code>s, and provide
|
||||
additional useful capabilities like in-place updating of elements.
|
||||
@@ -355,7 +354,7 @@ in practice greatly reduces the freedom in choosing an equality predicate.
|
||||
|
||||
<p>
|
||||
The lookup interface of hashed indices consists in member functions
|
||||
<code>find</code>, <code>count</code>, <code>contains</code> and <code>equal_range</code>.
|
||||
<code>find</code>, <code>count</code> and <code>equal_range</code>.
|
||||
Note that <code>lower_bound</code> and <code>upper_bound</code> are not
|
||||
provided, as there is no intrinsic ordering of keys in this type of indices.
|
||||
</p>
|
||||
@@ -757,7 +756,7 @@ specifically designed for handling the elements of a container,
|
||||
and not only benefit from the iterator orientation of container interfaces,
|
||||
but are also capable of exposing many more programming bugs than raw pointers, both
|
||||
at compile and run time. <code>iterator_to</code> is thus meant to be used
|
||||
in scenarios where access via iterators is not suitable or desirable:
|
||||
in scenarios where access via iterators is not suitable or desireable:
|
||||
<ul>
|
||||
<li>Interoperability with preexisting APIs based on pointers or references.</li>
|
||||
<li>Publication of pointer-based interfaces (for instance, when
|
||||
@@ -775,113 +774,6 @@ in scenarios where access via iterators is not suitable or desirable:
|
||||
</ul>
|
||||
</p>
|
||||
|
||||
<h2><a name="node_handling">Node handling operations</a></h2>
|
||||
|
||||
<p>
|
||||
Using direct node manipulation, elements can be passed between
|
||||
<code>multi_index_container</code>s without actually copying them:
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=comment>// move an employee to the retiree archive</span>
|
||||
<span class=keyword>void</span> <span class=identifier>move_to_retirement</span><span class=special>(</span><span class=keyword>int</span> <span class=identifier>ssnumber</span><span class=special>,</span><span class=identifier>employee_set</span><span class=special>&</span> <span class=identifier>es</span><span class=special>,</span><span class=identifier>employee_set</span><span class=special>&</span> <span class=identifier>archive</span><span class=special>)</span>
|
||||
<span class=special>{</span>
|
||||
<span class=comment>// assume employee_set has an index on SS number(not shown before)</span>
|
||||
<span class=comment>// extract the employee with given SS number to a node handle</span>
|
||||
<span class=identifier>employee_set_by_ssn</span><span class=special>::</span><span class=identifier>node_type</span> <span class=identifier>node</span><span class=special>=</span><span class=identifier>es</span><span class=special>.</span><span class=identifier>get</span><span class=special><</span><span class=identifier>ssn</span><span class=special>>().</span><span class=identifier>extract</span><span class=special>(</span><span class=identifier>ssnumber</span><span class=special>);</span>
|
||||
|
||||
<span class=keyword>if</span><span class=special>(!</span><span class=identifier>node</span><span class=special>.</span><span class=identifier>empty</span><span class=special>()){</span> <span class=comment>// employee found
|
||||
// re-insert into archive (note the use of std::move)</span>
|
||||
<span class=identifier>archive</span><span class=special>.</span><span class=identifier>insert</span><span class=special>(</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>move</span><span class=special>(</span><span class=identifier>node</span><span class=special>));</span>
|
||||
<span class=special>}</span>
|
||||
<span class=special>}</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
In the example, the internal node is transferred as-is from <code>es</code> to <code>archive</code>,
|
||||
which is more efficient than erasing from the source and recreating in destination.
|
||||
<code>node_type</code> is a move-only class used to pass nodes around, and its interface follows
|
||||
that of the <a href="https://en.cppreference.com/w/cpp/container/node_handle">homonym type</a>
|
||||
for C++ associative containers (set containers version). Boost.MultiIndex provides node extraction
|
||||
and insertion operations for all index types, including sequenced ones (by contrast,
|
||||
<code>std::list</code> does not have such features):
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>int</span><span class=special>,</span>
|
||||
<span class=identifier>indexed_by</span><span class=special><</span>
|
||||
<span class=identifier>sequenced</span><span class=special><>,</span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>></span>
|
||||
<span class=special>></span>
|
||||
<span class=special>></span> <span class=identifier>src</span><span class=special>;</span>
|
||||
|
||||
<span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>int</span><span class=special>,</span>
|
||||
<span class=identifier>indexed_by</span><span class=special><</span>
|
||||
<span class=identifier>sequenced</span><span class=special><>,</span>
|
||||
<span class=identifier>ordered_non_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>>,</span> <span class=identifier>std</span><span class=special>::</span><span class=identifier>greater</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>></span>
|
||||
<span class=special>></span>
|
||||
<span class=special>></span> <span class=identifier>dst</span><span class=special>;</span>
|
||||
|
||||
<span class=special>...</span>
|
||||
|
||||
<span class=comment>// transfer even numbers from src to dst</span>
|
||||
<span class=keyword>for</span><span class=special>(</span><span class=keyword>auto</span> <span class=identifier>first</span><span class=special>=</span><span class=identifier>src</span><span class=special>.</span><span class=identifier>begin</span><span class=special>(),</span><span class=identifier>last</span><span class=special>=</span><span class=identifier>src</span><span class=special>.</span><span class=identifier>end</span><span class=special>();</span><span class=identifier>first</span><span class=special>!=</span><span class=identifier>last</span><span class=special>;){</span>
|
||||
<span class=keyword>if</span><span class=special>(*</span><span class=identifier>first</span><span class=special>%</span><span class=number>2</span><span class=special>==</span><span class=number>0</span><span class=special>)</span> <span class=identifier>dst</span><span class=special>.</span><span class=identifier>insert</span><span class=special>(</span><span class=identifier>dst</span><span class=special>.</span><span class=identifier>end</span><span class=special>(),</span><span class=identifier>src</span><span class=special>.</span><span class=identifier>extract</span><span class=special>(</span><span class=identifier>first</span><span class=special>++));</span>
|
||||
<span class=keyword>else</span> <span class=special>++</span><span class=identifier>first</span><span class=special>;</span>
|
||||
<span class=special>}</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
Note that <code>src</code> and <code>dst</code> are of different types,
|
||||
yet transfer is possible. Two <code>multi_index_container</code>s are
|
||||
node-compatible (that is, they use the same <code>node_type</code>) if
|
||||
they have the same element and allocator types and their respective indices match
|
||||
one by one without regard to whether they are unique or non-unique or to
|
||||
their particular configuration parameters: they are both ordered, or
|
||||
both sequenced, etc.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
Alternatively, direct node transfer between two containers can be done without
|
||||
keeping intervening <code>node_type</code>s thanks to <code>merge</code> (key-based
|
||||
indices) and <code>splice</code> (non key-based indices).
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=comment>// move older employees to retirement</span>
|
||||
<span class=keyword>void</span> <span class=identifier>move_to_retirement_by_age</span><span class=special>(
|
||||
</span><span class=keyword>int</span> <span class=identifier>max_age</span><span class=special>,</span><span class=identifier>employee_set</span><span class=special>&</span> <span class=identifier>es</span><span class=special>,</span><span class=identifier>employee_set</span><span class=special>&</span> <span class=identifier>archive</span><span class=special>)</span>
|
||||
<span class=special>{</span>
|
||||
<span class=comment>// assume employee_set has an index on age (not shown before)</span>
|
||||
<span class=identifier>employee_set_by_age</span><span class=special>&</span> <span class=identifier>ea</span><span class=special>=</span><span class=identifier>es</span><span class=special>.</span><span class=identifier>get</span><span class=special><</span><span class=identifier>age</span><span class=special>>();</span>
|
||||
|
||||
<span class=comment>// archive employees with age>max_age</span>
|
||||
<span class=identifier>archive</span><span class=special>.</span><span class=identifier>merge</span><span class=special>(</span><span class=identifier>ea</span><span class=special>,</span><span class=identifier>ea</span><span class=special>.</span><span class=identifier>upper_bound</span><span class=special>(</span><span class=identifier>max_age</span><span class=special>),</span><span class=identifier>ea</span><span class=special>.</span><span class=identifier>end</span><span class=special>());</span>
|
||||
<span class=special>}</span>
|
||||
|
||||
<span class=special>...</span>
|
||||
|
||||
<span class=comment>// transfer even numbers from src to dst</span>
|
||||
<span class=keyword>for</span><span class=special>(</span><span class=keyword>auto</span> <span class=identifier>first</span><span class=special>=</span><span class=identifier>src</span><span class=special>.</span><span class=identifier>begin</span><span class=special>(),</span><span class=identifier>last</span><span class=special>=</span><span class=identifier>src</span><span class=special>.</span><span class=identifier>end</span><span class=special>();</span><span class=identifier>first</span><span class=special>!=</span><span class=identifier>last</span><span class=special>;){</span>
|
||||
<span class=keyword>if</span><span class=special>(*</span><span class=identifier>first</span><span class=special>%</span><span class=number>2</span><span class=special>==</span><span class=number>0</span><span class=special>)</span> <span class=identifier>dst</span><span class=special>.</span><span class=identifier>splice</span><span class=special>(</span><span class=identifier>dst</span><span class=special>.</span><span class=identifier>end</span><span class=special>(),</span><span class=identifier>src</span><span class=special>,</span><span class=identifier>first</span><span class=special>++);</span>
|
||||
<span class=keyword>else</span> <span class=special>++</span><span class=identifier>first</span><span class=special>;</span>
|
||||
<span class=special>}</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
There are overloads of <code>merge</code>/<code>splice</code> for transferring a single element,
|
||||
a range between two iterators and an entire container: for further details, consult
|
||||
for instance the reference for <a href="../reference/ord_indices.html#merge">ordered indices</a> and for
|
||||
<a href="../reference/seq_indices.html#splice">sequenced indices</a>
|
||||
(the rest of indices provide one interface or the other).
|
||||
Please note that sequenced and random access indices do also have an operation called <code>merge</code>,
|
||||
but this follows the specification of <code>std::list::merge</code>, which has a somewhat
|
||||
different behavior (source and destination are required to be ordered by the same criterion). This is
|
||||
a rather confusing naming issue that Boost.MultiIndex simply inherits from the C++ standard.
|
||||
</p>
|
||||
|
||||
<h2><a name="ordered_node_compression">Ordered indices node compression</a></h2>
|
||||
|
||||
<p>
|
||||
@@ -929,9 +821,9 @@ Key extraction
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised August 16th 2021</p>
|
||||
<p>Revised August 6th 2018</p>
|
||||
|
||||
<p>© Copyright 2003-2021 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2018 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
@@ -98,10 +98,10 @@ of the element and do not depend on external data.
|
||||
A key extractor is called <i>read/write</i> if it returns a non-constant reference
|
||||
to the key when passed a non-constant element, and it is called <i>read-only</i>
|
||||
otherwise. Boost.MultiIndex requires that the key extractor be read/write
|
||||
when using the <code>modify_key</code> member function of key-based
|
||||
when using the <code>modify_key</code> member function of ordered and hashed
|
||||
indices. In all other situations, read-only extractors suffice.
|
||||
The section on <a href="#advanced_key_extractors">advanced features
|
||||
of Boost.MultiIndex key extractors</a> shows typical situations on which the predefined
|
||||
of Boost.MultiIndex key extractors</a> details which of the predefined
|
||||
key extractors are read/write.
|
||||
</p>
|
||||
|
||||
@@ -494,7 +494,7 @@ The analogous concept in Boost.MultiIndex is modeled by means of
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
<code>composite_key</code> accepts several key extractors on the same
|
||||
<code>composite_key</code> accepts two or more key extractors on the same
|
||||
value (here, <code>phonebook_entry</code>). Lookup operations on a composite
|
||||
key are accomplished by passing tuples with the values searched:
|
||||
</p>
|
||||
@@ -1126,9 +1126,9 @@ Container creation
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised November 1st 2025</p>
|
||||
<p>Revised June 11th 2019</p>
|
||||
|
||||
<p>© Copyright 2003-2025 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2019 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
@@ -40,8 +40,8 @@ Boost.MultiIndex reference
|
||||
</li>
|
||||
<li><a href="#metaprogrammming">Metaprogramming and <code>multi_index_container</code></a>
|
||||
<ul>
|
||||
<li><a href="#analysis">Analysis</a></li>
|
||||
<li><a href="#synthesis">Synthesis</a></li>
|
||||
<li><a href="#mpl_analysis">MPL analysis</a></li>
|
||||
<li><a href="#mpl_synthesis">MPL synthesis</a></li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
@@ -53,7 +53,7 @@ Boost.MultiIndex reference
|
||||
containers</a></h3>
|
||||
|
||||
<p>
|
||||
Academic motivations aside, there is a practical interest in emulating standard
|
||||
Academic movitations aside, there is a practical interest in emulating standard
|
||||
associative containers by means of <code>multi_index_container</code>, namely to take
|
||||
advantage of extended functionalities provided by <code>multi_index_container</code> for
|
||||
lookup, range querying and updating.
|
||||
@@ -266,10 +266,11 @@ or, if the default value <code>Allocator=std::allocator<T></code> is used:
|
||||
|
||||
<p>
|
||||
Boost.MultiIndex provides a number of facilities intended to allow the analysis and
|
||||
synthesis of <code>multi_index_container</code> instantiations with metaprogramming.
|
||||
synthesis of <code>multi_index_container</code> instantiations by
|
||||
<a href="../../../../libs/mpl/doc/index.html">MPL</a> metaprograms.
|
||||
</p>
|
||||
|
||||
<h3><a name="analysis">Analysis</a></h3>
|
||||
<h3><a name="mpl_analysis">MPL analysis</a></h3>
|
||||
|
||||
<p>
|
||||
Given a <code>multi_index_container</code> instantiation, the following nested types are
|
||||
@@ -281,47 +282,39 @@ definition of the <code>multi_index_container</code>:
|
||||
<li><code>iterator_type_list</code>,</li>
|
||||
<li><code>const_iterator_type_list</code>.</li>
|
||||
</ul>
|
||||
Each of these types is an
|
||||
<a href="../../../../libs/mp11/doc/html/mp11.html#definitions">Mp11 list</a>
|
||||
with as many elements as indices
|
||||
Each of these types is an MPL sequence with as many elements as indices
|
||||
comprise the <code>multi_index_container</code>: for instance, the <code>n</code>-th
|
||||
element of <code>iterator_type_list</code> is the same as
|
||||
<code>nth_index<n>::type::iterator</code>. Boost.Mp11 makes it very easy
|
||||
to inspect and manipulate these lists:
|
||||
<code>nth_index<n>::type::iterator</code>.
|
||||
</p>
|
||||
|
||||
<p>
|
||||
A subtle but important distinction exists between
|
||||
<code>index_specifier_type_list</code> and <code>index_type_list</code>:
|
||||
the former typelist holds the index <i>specifiers</i>
|
||||
with which the <code>multi_index_container</code> instantiation was defined,
|
||||
while the latter gives access to the actual implementation classes
|
||||
corresponding to each specifier. An example will help to clarify
|
||||
this distinction. Given the instantiation:
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=keyword>using</span> <span class=identifier>indexed_t</span><span class=special>=</span><span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>typedef</span> <span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>int</span><span class=special>,</span>
|
||||
<span class=identifier>indexed_by</span><span class=special><</span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>>,</span>
|
||||
<span class=identifier>sequenced</span><span class=special><></span>
|
||||
<span class=special>></span>
|
||||
<span class=special>>;</span>
|
||||
|
||||
<span class=identifier>boost</span><span class=special>::</span><span class=identifier>mp11</span><span class=special>::</span><span class=identifier>mp_for_each</span><span class=special><</span><span class=identifier>indexed_t</span><span class=special>::</span><span class=identifier>index_specifier_type_list</span><span class=special>>([](</span><span class=keyword>auto</span> <span class=identifier>I</span><span class=special>){</span>
|
||||
<span class=identifier>std</span><span class=special>::</span><span class=identifier>cout</span> <span class=special><<</span> <span class=identifier>boost</span><span class=special>::</span><span class=identifier>typeindex</span><span class=special>::</span><span class=identifier>type_id</span><span class=special><</span><span class=identifier>decltype</span><span class=special>(</span><span class=identifier>I</span><span class=special>)>().</span><span class=identifier>pretty_name</span><span class=special>()</span> <span class=special><<</span> <span class=string>"\n"</span><span class=special>;</span>
|
||||
<span class=special>});</span>
|
||||
|
||||
<span class=comment>// Output:
|
||||
//
|
||||
// struct boost::multi_index::ordered_unique<struct boost::multi_index::identity<int>,void,void>
|
||||
// struct boost::multi_index::sequenced<struct boost::multi_index::tag<> ></span>
|
||||
<span class=special>></span> <span class=identifier>indexed_t</span><span class=special>;</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
A subtle but important distinction exists between
|
||||
<code>index_specifier_type_list</code> and <code>index_type_list</code>:
|
||||
the former list holds the index <i>specifiers</i>
|
||||
with which the <code>multi_index_container</code> instantiation was defined,
|
||||
while the latter gives access to the actual implementation classes
|
||||
corresponding to each specifier. In the example above,
|
||||
<code>indexed_t::index_specifier_type_list</code> is a type list with
|
||||
elements
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>></span><span class=special>></span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>></span>
|
||||
<span class=identifier>sequenced</span><span class=special><></span>
|
||||
</pre></blockquote>
|
||||
|
||||
@@ -335,18 +328,21 @@ while <code>indexed_t::index_type_list</code> holds the types
|
||||
</pre></blockquote>
|
||||
|
||||
<p>
|
||||
so the lists are radically different.
|
||||
so the typelists are radically different. Check the
|
||||
<a href="../reference/multi_index_container.html#types">reference</a>
|
||||
for the exact MPL sequence concepts modeled by these type lists.
|
||||
</p>
|
||||
|
||||
<h3><a name="synthesis">Synthesis</a></h3>
|
||||
<h3><a name="mpl_synthesis">MPL synthesis</a></h3>
|
||||
|
||||
<p>
|
||||
Although typically indices are specified by means of the
|
||||
<code>indexed_by</code> construct, actually any Mp11 list can be provided instead:
|
||||
<code>indexed_by</code> construct, actually any MPL sequence of
|
||||
index specifiers can be provided instead:
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=keyword>using</span> <span class=identifier>index_list_t</span><span class=special>=</span><span class=identifier>std</span><span class=special>::</span><span class=identifier>tuple</span><span class=special><</span><span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>>,</span><span class=identifier>sequenced</span><span class=special><>></span> <span class=special>;</span>
|
||||
<span class=keyword>typedef</span> <span class=identifier>mpl</span><span class=special>::</span><span class=identifier>vector</span><span class=special><</span><span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>>,</span><span class=identifier>sequenced</span><span class=special><></span> <span class=special>></span> <span class=identifier>index_list_t</span><span class=special>;</span>
|
||||
|
||||
<span class=keyword>typedef</span> <span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>int</span><span class=special>,</span>
|
||||
@@ -356,30 +352,30 @@ Although typically indices are specified by means of the
|
||||
|
||||
<p>
|
||||
This possibility enables the synthesis of instantiations of
|
||||
<code>multi_index_container</code> through metaprogramming, as the following
|
||||
<code>multi_index_container</code> through MPL metaprograms, as the following
|
||||
example shows:
|
||||
</p>
|
||||
|
||||
<blockquote><pre>
|
||||
<span class=comment>// original multi_index_container instantiation</span>
|
||||
<span class=keyword>using</span> <span class=identifier>indexed_t1</span><span class=special>=</span><span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>typedef</span> <span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>int</span><span class=special>,</span>
|
||||
<span class=identifier>indexed_by</span><span class=special><</span>
|
||||
<span class=identifier>ordered_unique</span><span class=special><</span><span class=identifier>identity</span><span class=special><</span><span class=keyword>int</span><span class=special>></span> <span class=special>></span>
|
||||
<span class=special>></span>
|
||||
<span class=special>>;</span>
|
||||
<span class=special>></span> <span class=identifier>indexed_t1</span><span class=special>;</span>
|
||||
|
||||
<span class=comment>// we take its index list and add an index</span>
|
||||
<span class=keyword>using</span> <span class=identifier>index_list_t2</span><span class=special>=</span><span class=identifier>boost</span><span class=special>::</span><span class=identifier>mp11</span><span class=special>::</span><span class=identifier>mp_push_front</span><span class=special><</span>
|
||||
<span class=keyword>typedef</span> <span class=identifier>boost</span><span class=special>::</span><span class=identifier>mpl</span><span class=special>::</span><span class=identifier>push_front</span><span class=special><</span>
|
||||
<span class=identifier>indexed_t1</span><span class=special>::</span><span class=identifier>index_specifier_type_list</span><span class=special>,</span>
|
||||
<span class=identifier>sequenced</span><span class=special><></span>
|
||||
<span class=special>>;</span>
|
||||
<span class=special>>::</span><span class=identifier>type</span> <span class=identifier>index_list_t</span><span class=special>;</span>
|
||||
|
||||
<span class=comment>// augmented multi_index_container</span>
|
||||
<span class=keyword>using</span> <span class=identifier>indexed_t2</span><span class=special>=</span><span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>typedef</span> <span class=identifier>multi_index_container</span><span class=special><</span>
|
||||
<span class=keyword>int</span><span class=special>,</span>
|
||||
<span class=identifier>index_list_t2</span>
|
||||
<span class=special>>;</span>
|
||||
<span class=identifier>index_list_t</span>
|
||||
<span class=special>></span> <span class=identifier>indexed_t2</span><span class=special>;</span>
|
||||
</pre></blockquote>
|
||||
|
||||
<hr>
|
||||
@@ -396,9 +392,9 @@ Boost.MultiIndex reference
|
||||
|
||||
<br>
|
||||
|
||||
<p>Revised October 25th 2025</p>
|
||||
<p>Revised November 7th 2008</p>
|
||||
|
||||
<p>© Copyright 2003-2025 Joaquín M López Muñoz.
|
||||
<p>© Copyright 2003-2008 Joaquín M López Muñoz.
|
||||
Distributed under the Boost Software
|
||||
License, Version 1.0. (See accompanying file <a href="../../../../LICENSE_1_0.txt">
|
||||
LICENSE_1_0.txt</a> or copy at <a href="http://www.boost.org/LICENSE_1_0.txt">
|
||||
|
||||
+13
-10
@@ -1,66 +1,69 @@
|
||||
# Boost.MultiIndex examples Jamfile
|
||||
#
|
||||
# Copyright 2003-2007 Joaqu�n M L�pez Mu�oz.
|
||||
# Copyright 2003-2007 Joaquín M López Muñoz.
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at
|
||||
# http://www.boost.org/LICENSE_1_0.txt)
|
||||
#
|
||||
# See http://www.boost.org/libs/multi_index for library home page.
|
||||
|
||||
project : requirements <library>/boost/multi_index//boost_multi_index ;
|
||||
|
||||
exe basic
|
||||
: basic.cpp
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe bimap
|
||||
: bimap.cpp
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe complex_structs
|
||||
: complex_structs.cpp
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe composite_keys
|
||||
: composite_keys.cpp
|
||||
/boost/tokenizer//boost_tokenizer
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe fun_key
|
||||
: fun_key.cpp
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe hashed
|
||||
: hashed.cpp
|
||||
/boost/tokenizer//boost_tokenizer
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe ip_allocator
|
||||
: ip_allocator.cpp
|
||||
/boost/interprocess//boost_interprocess
|
||||
: <threading>multi
|
||||
: <include>$(BOOST_ROOT) <threading>multi
|
||||
;
|
||||
|
||||
exe non_default_ctor
|
||||
: non_default_ctor.cpp
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe random_access
|
||||
: random_access.cpp
|
||||
/boost/tokenizer//boost_tokenizer
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe rearrange
|
||||
: rearrange.cpp
|
||||
/boost/random//boost_random
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe sequenced
|
||||
: sequenced.cpp
|
||||
/boost/tokenizer//boost_tokenizer
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
exe serialization
|
||||
: serialization.cpp
|
||||
/boost/serialization//boost_serialization
|
||||
: <include>$(BOOST_ROOT)
|
||||
;
|
||||
|
||||
+9
-5
@@ -1,6 +1,6 @@
|
||||
/* Boost.MultiIndex basic example.
|
||||
*
|
||||
* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -47,8 +47,12 @@ struct id{};
|
||||
struct name{};
|
||||
struct age{};
|
||||
|
||||
/* see Compiler specifics: Use of member_offset for info on
|
||||
* BOOST_MULTI_INDEX_MEMBER
|
||||
*/
|
||||
|
||||
/* Define a multi_index_container of employees with following indices:
|
||||
* - a unique index sorted by employee::id,
|
||||
* - a unique index sorted by employee::int,
|
||||
* - a non-unique index sorted by employee::name,
|
||||
* - a non-unique index sorted by employee::age.
|
||||
*/
|
||||
@@ -57,11 +61,11 @@ typedef multi_index_container<
|
||||
employee,
|
||||
indexed_by<
|
||||
ordered_unique<
|
||||
tag<id>, member<employee,int,&employee::id> >,
|
||||
tag<id>, BOOST_MULTI_INDEX_MEMBER(employee,int,id)>,
|
||||
ordered_non_unique<
|
||||
tag<name>,member<employee,std::string,&employee::name> >,
|
||||
tag<name>,BOOST_MULTI_INDEX_MEMBER(employee,std::string,name)>,
|
||||
ordered_non_unique<
|
||||
tag<age>, member<employee,int,&employee::age> > >
|
||||
tag<age>, BOOST_MULTI_INDEX_MEMBER(employee,int,age)> >
|
||||
> employee_set;
|
||||
|
||||
template<typename Tag,typename MultiIndexContainer>
|
||||
|
||||
+45
-1
@@ -1,6 +1,6 @@
|
||||
/* Boost.MultiIndex example of a bidirectional map.
|
||||
*
|
||||
* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Copyright 2003-2009 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -44,6 +44,30 @@ struct bidirectional_map
|
||||
ToType second;
|
||||
};
|
||||
|
||||
#if defined(BOOST_NO_POINTER_TO_MEMBER_TEMPLATE_PARAMETERS) ||\
|
||||
defined(BOOST_MSVC)&&(BOOST_MSVC<1300) ||\
|
||||
defined(BOOST_INTEL_CXX_VERSION)&&defined(_MSC_VER)&&\
|
||||
(BOOST_INTEL_CXX_VERSION<=700)
|
||||
|
||||
/* see Compiler specifics: Use of member_offset for info on member<> and
|
||||
* member_offset<>
|
||||
*/
|
||||
|
||||
BOOST_STATIC_CONSTANT(unsigned,from_offset=offsetof(value_type,first));
|
||||
BOOST_STATIC_CONSTANT(unsigned,to_offset =offsetof(value_type,second));
|
||||
|
||||
typedef multi_index_container<
|
||||
value_type,
|
||||
indexed_by<
|
||||
ordered_unique<
|
||||
tag<from>,member_offset<value_type,FromType,from_offset> >,
|
||||
ordered_unique<
|
||||
tag<to>, member_offset<value_type,ToType,to_offset> >
|
||||
>
|
||||
> type;
|
||||
|
||||
#else
|
||||
|
||||
/* A bidirectional map can be simulated as a multi_index_container
|
||||
* of pairs of (FromType,ToType) with two unique indices, one
|
||||
* for each member of the pair.
|
||||
@@ -58,6 +82,8 @@ struct bidirectional_map
|
||||
tag<to>, member<value_type,ToType,&value_type::second> >
|
||||
>
|
||||
> type;
|
||||
|
||||
#endif
|
||||
};
|
||||
|
||||
/* a dictionary is a bidirectional map from strings to strings */
|
||||
@@ -82,6 +108,22 @@ int main()
|
||||
std::string word;
|
||||
std::getline(std::cin,word);
|
||||
|
||||
#if defined(BOOST_NO_MEMBER_TEMPLATES) /* use global get<> and family instead */
|
||||
|
||||
dictionary::iterator it=get<from>(d).find(word);
|
||||
if(it!=d.end()){
|
||||
std::cout<<word<<" is said "<<it->second<<" in English"<<std::endl;
|
||||
}
|
||||
else{
|
||||
nth_index<dictionary,1>::type::iterator it2=get<1>(d).find(word);
|
||||
if(it2!=get<1>(d).end()){
|
||||
std::cout<<word<<" is said "<<it2->first<<" in Spanish"<<std::endl;
|
||||
}
|
||||
else std::cout<<"No such word in the dictionary"<<std::endl;
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
/* search the queried word on the from index (Spanish) */
|
||||
|
||||
dictionary::iterator it=d.get<from>().find(word);
|
||||
@@ -101,5 +143,7 @@ int main()
|
||||
else std::cout<<"No such word in the dictionary"<<std::endl;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
+16
-12
@@ -1,6 +1,6 @@
|
||||
/* Boost.MultiIndex example: complex searches and foreign keys.
|
||||
*
|
||||
* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Copyright 2003-2008 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -88,6 +88,10 @@ struct car_model
|
||||
}
|
||||
};
|
||||
|
||||
/* see Compiler specifics: Use of member_offset for info on
|
||||
* BOOST_MULTI_INDEX_MEMBER
|
||||
*/
|
||||
|
||||
/* Car manufacturers are stored in a multi_index_container with one single
|
||||
* index on the name member. This is functionally equivalent to an std::set,
|
||||
* though in this latter case we woud have to define a non-default comparison
|
||||
@@ -98,7 +102,7 @@ typedef multi_index_container<
|
||||
car_manufacturer,
|
||||
indexed_by<
|
||||
ordered_unique<
|
||||
member<car_manufacturer,std::string,&car_manufacturer::name>
|
||||
BOOST_MULTI_INDEX_MEMBER(car_manufacturer,std::string,name)
|
||||
>
|
||||
>
|
||||
> car_manufacturer_table;
|
||||
@@ -114,18 +118,18 @@ typedef multi_index_container<
|
||||
car_model,
|
||||
indexed_by<
|
||||
ordered_unique<
|
||||
tag<model>,member<car_model,std::string,&car_model::model>
|
||||
tag<model>,BOOST_MULTI_INDEX_MEMBER(car_model,std::string,model)
|
||||
>,
|
||||
ordered_non_unique<
|
||||
tag<manufacturer>,
|
||||
key_from_key<
|
||||
member<car_manufacturer,const std::string,&car_manufacturer::name>,
|
||||
member<
|
||||
car_model,const car_manufacturer *,&car_model::manufacturer>
|
||||
BOOST_MULTI_INDEX_MEMBER(car_manufacturer,const std::string,name),
|
||||
BOOST_MULTI_INDEX_MEMBER(
|
||||
car_model,const car_manufacturer *,manufacturer)
|
||||
>
|
||||
>,
|
||||
ordered_non_unique<
|
||||
tag<price>,member<car_model,int,&car_model::price>
|
||||
tag<price>,BOOST_MULTI_INDEX_MEMBER(car_model,int,price)
|
||||
>
|
||||
>
|
||||
> car_table;
|
||||
@@ -134,7 +138,7 @@ typedef multi_index_container<
|
||||
* actual objects. These views are used in the complex search performed
|
||||
* in the program. Resorting to multi_index of pointers eliminates
|
||||
* unnecessary copying of objects, and provides us with an opportunity
|
||||
* to show how boost::multi_index::member can be used with pointer
|
||||
* to show how BOOST_MULTI_INDEX_MEMBER can be used with pointer
|
||||
* type elements.
|
||||
* car_table_price_view indexes (pointers to) car_models by price.
|
||||
*/
|
||||
@@ -142,7 +146,7 @@ typedef multi_index_container<
|
||||
typedef multi_index_container<
|
||||
const car_model*,
|
||||
indexed_by<
|
||||
ordered_non_unique<member<car_model,const int,&car_model::price> >
|
||||
ordered_non_unique<BOOST_MULTI_INDEX_MEMBER(car_model,const int,price)>
|
||||
>
|
||||
> car_table_price_view;
|
||||
|
||||
@@ -155,9 +159,9 @@ typedef multi_index_container<
|
||||
indexed_by<
|
||||
ordered_non_unique<
|
||||
key_from_key<
|
||||
member<car_manufacturer,const std::string,&car_manufacturer::name>,
|
||||
member<
|
||||
car_model,const car_manufacturer * const,&car_model::manufacturer>
|
||||
BOOST_MULTI_INDEX_MEMBER(car_manufacturer,const std::string,name),
|
||||
BOOST_MULTI_INDEX_MEMBER(
|
||||
car_model,const car_manufacturer * const,manufacturer)
|
||||
>
|
||||
>
|
||||
>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* Boost.MultiIndex example of composite keys.
|
||||
*
|
||||
* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Copyright 2003-2008 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -57,22 +57,26 @@ struct file_entry
|
||||
* file and size. These indices are firstly ordered by directory, as commands
|
||||
* work on a current directory basis. Composite keys are just fine to model
|
||||
* this.
|
||||
* NB: The use of derivation here instead of simple typedef helps produce
|
||||
* shorter symbol names in compilation
|
||||
* NB: The use of derivation here instead of simple typedef is explained in
|
||||
* Compiler specifics: type hiding.
|
||||
*/
|
||||
|
||||
struct name_key:composite_key<
|
||||
file_entry,
|
||||
member<file_entry,const file_entry*,&file_entry::dir>,
|
||||
member<file_entry,std::string,&file_entry::name>
|
||||
BOOST_MULTI_INDEX_MEMBER(file_entry,const file_entry*,dir),
|
||||
BOOST_MULTI_INDEX_MEMBER(file_entry,std::string,name)
|
||||
>{};
|
||||
|
||||
struct size_key:composite_key<
|
||||
file_entry,
|
||||
member<file_entry,const file_entry* const,&file_entry::dir>,
|
||||
member<file_entry,unsigned,&file_entry::size>
|
||||
BOOST_MULTI_INDEX_MEMBER(file_entry,const file_entry* const,dir),
|
||||
BOOST_MULTI_INDEX_MEMBER(file_entry,unsigned,size)
|
||||
>{};
|
||||
|
||||
/* see Compiler specifics: composite_key in compilers without partial
|
||||
* template specialization, for info on composite_key_result_less
|
||||
*/
|
||||
|
||||
typedef multi_index_container<
|
||||
file_entry,
|
||||
indexed_by<
|
||||
|
||||
+4
-2
@@ -1,6 +1,6 @@
|
||||
/* Boost.MultiIndex example of functions used as key extractors.
|
||||
*
|
||||
* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Copyright 2003-2008 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -54,13 +54,15 @@ std::string::size_type name_record_length(const name_record& r)
|
||||
|
||||
/* multi_index_container with indices based on name_record::name()
|
||||
* and name_record_length().
|
||||
* See Compiler specifics: Use of const_mem_fun_explicit and
|
||||
* mem_fun_explicit for info on BOOST_MULTI_INDEX_CONST_MEM_FUN.
|
||||
*/
|
||||
|
||||
typedef multi_index_container<
|
||||
name_record,
|
||||
indexed_by<
|
||||
ordered_unique<
|
||||
const_mem_fun<name_record,std::string,&name_record::name>
|
||||
BOOST_MULTI_INDEX_CONST_MEM_FUN(name_record,std::string,name)
|
||||
>,
|
||||
ordered_non_unique<
|
||||
global_fun<const name_record&,std::string::size_type,name_record_length>
|
||||
|
||||
+19
-15
@@ -1,6 +1,6 @@
|
||||
/* Boost.MultiIndex example of use of hashed indices.
|
||||
*
|
||||
* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Copyright 2003-2008 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -37,15 +37,19 @@ struct word_counter_entry
|
||||
word_counter_entry(std::string word_):word(word_),occurrences(0){}
|
||||
};
|
||||
|
||||
/* see Compiler specifics: Use of member_offset for info on
|
||||
* BOOST_MULTI_INDEX_MEMBER
|
||||
*/
|
||||
|
||||
typedef multi_index_container<
|
||||
word_counter_entry,
|
||||
indexed_by<
|
||||
ordered_non_unique<
|
||||
member<word_counter_entry,unsigned int,&word_counter_entry::occurrences>,
|
||||
BOOST_MULTI_INDEX_MEMBER(word_counter_entry,unsigned int,occurrences),
|
||||
std::greater<unsigned int> /* sorted beginning with most frequent */
|
||||
>,
|
||||
hashed_unique<
|
||||
member<word_counter_entry,std::string,&word_counter_entry::word>
|
||||
BOOST_MULTI_INDEX_MEMBER(word_counter_entry,std::string,word)
|
||||
>
|
||||
>
|
||||
> word_counter;
|
||||
@@ -66,23 +70,23 @@ int main()
|
||||
|
||||
std::string text=
|
||||
"En un lugar de la Mancha, de cuyo nombre no quiero acordarme, no ha "
|
||||
"mucho tiempo que vivía un hidalgo de los de lanza en astillero, adarga "
|
||||
"antigua, rocín flaco y galgo corredor. Una olla de algo más vaca que "
|
||||
"carnero, salpicón las más noches, duelos y quebrantos los sábados, "
|
||||
"lantejas los viernes, algún palomino de añadidura los domingos, "
|
||||
"consumían las tres partes de su hacienda. El resto della concluían sayo "
|
||||
"mucho tiempo que vivía un hidalgo de los de lanza en astillero, adarga "
|
||||
"antigua, rocín flaco y galgo corredor. Una olla de algo más vaca que "
|
||||
"carnero, salpicón las más noches, duelos y quebrantos los sábados, "
|
||||
"lantejas los viernes, algún palomino de añadidura los domingos, "
|
||||
"consumían las tres partes de su hacienda. El resto della concluían sayo "
|
||||
"de velarte, calzas de velludo para las fiestas, con sus pantuflos de lo "
|
||||
"mesmo, y los días de entresemana se honraba con su vellorí de lo más "
|
||||
"fino. Tenía en su casa una ama que pasaba de los cuarenta, y una "
|
||||
"mesmo, y los días de entresemana se honraba con su vellorí de lo más "
|
||||
"fino. Tenía en su casa una ama que pasaba de los cuarenta, y una "
|
||||
"sobrina que no llegaba a los veinte, y un mozo de campo y plaza, que "
|
||||
"así ensillaba el rocín como tomaba la podadera. Frisaba la edad de "
|
||||
"nuestro hidalgo con los cincuenta años; era de complexión recia, seco "
|
||||
"así ensillaba el rocín como tomaba la podadera. Frisaba la edad de "
|
||||
"nuestro hidalgo con los cincuenta años; era de complexión recia, seco "
|
||||
"de carnes, enjuto de rostro, gran madrugador y amigo de la caza. "
|
||||
"Quieren decir que tenía el sobrenombre de Quijada, o Quesada, que en "
|
||||
"Quieren decir que tenía el sobrenombre de Quijada, o Quesada, que en "
|
||||
"esto hay alguna diferencia en los autores que deste caso escriben; "
|
||||
"aunque, por conjeturas verosímiles, se deja entender que se llamaba "
|
||||
"aunque, por conjeturas verosímiles, se deja entender que se llamaba "
|
||||
"Quejana. Pero esto importa poco a nuestro cuento; basta que en la "
|
||||
"narración dél no se salga un punto de la verdad.";
|
||||
"narración dél no se salga un punto de la verdad.";
|
||||
|
||||
/* feed the text into the container */
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* Boost.MultiIndex example of use of Boost.Interprocess allocators.
|
||||
*
|
||||
* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
* Copyright 2003-2008 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -10,6 +10,7 @@
|
||||
|
||||
#if !defined(NDEBUG)
|
||||
#define BOOST_MULTI_INDEX_ENABLE_INVARIANT_CHECKING
|
||||
#define BOOST_MULTI_INDEX_ENABLE_SAFE_MODE
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
@@ -103,18 +104,22 @@ struct partial_str_less
|
||||
* * We are using a Boost.Interprocess specific allocator.
|
||||
*/
|
||||
|
||||
/* see Compiler specifics: Use of member_offset for info on
|
||||
* BOOST_MULTI_INDEX_MEMBER
|
||||
*/
|
||||
|
||||
typedef multi_index_container<
|
||||
book,
|
||||
indexed_by<
|
||||
ordered_non_unique<
|
||||
member<book,shared_string,&book::author>
|
||||
BOOST_MULTI_INDEX_MEMBER(book,shared_string,author)
|
||||
>,
|
||||
ordered_non_unique<
|
||||
member<book,shared_string,&book::name>,
|
||||
BOOST_MULTI_INDEX_MEMBER(book,shared_string,name),
|
||||
partial_str_less
|
||||
>,
|
||||
ordered_non_unique<
|
||||
member<book,unsigned,&book::prize>
|
||||
BOOST_MULTI_INDEX_MEMBER(book,unsigned,prize)
|
||||
>
|
||||
>,
|
||||
bip::allocator<book,bip::managed_mapped_file::segment_manager>
|
||||
|
||||
+20
-6
@@ -1,6 +1,6 @@
|
||||
/* Boost.MultiIndex example of use of rearrange facilities.
|
||||
*
|
||||
* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Copyright 2003-2015 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,6 +14,7 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp>
|
||||
#include <boost/detail/iterator.hpp>
|
||||
#include <boost/multi_index_container.hpp>
|
||||
#include <boost/multi_index/random_access_index.hpp>
|
||||
#include <boost/random/binomial_distribution.hpp>
|
||||
@@ -22,9 +23,12 @@
|
||||
#include <algorithm>
|
||||
#include <iostream>
|
||||
#include <iterator>
|
||||
#include <random>
|
||||
#include <vector>
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_HDR_RANDOM)
|
||||
#include <random>
|
||||
#endif
|
||||
|
||||
using boost::multi_index_container;
|
||||
using namespace boost::multi_index;
|
||||
|
||||
@@ -136,11 +140,11 @@ void riffle_shuffle(
|
||||
{
|
||||
static boost::mt19937 rnd_gen;
|
||||
|
||||
typedef typename std::iterator_traits<
|
||||
RandomAccessIterator>::difference_type difference_type;
|
||||
typedef typename boost::detail::iterator_traits<
|
||||
RandomAccessIterator>::difference_type difference_type;
|
||||
typedef boost::binomial_distribution<
|
||||
difference_type> rnd_cut_select_type;
|
||||
typedef boost::uniform_real<> rnd_deck_select_type;
|
||||
difference_type> rnd_cut_select_type;
|
||||
typedef boost::uniform_real<> rnd_deck_select_type;
|
||||
|
||||
rnd_cut_select_type cut_select(last-first);
|
||||
RandomAccessIterator middle=first+cut_select(rnd_gen);
|
||||
@@ -194,12 +198,22 @@ struct random_shuffler
|
||||
|
||||
private:
|
||||
deck_view dv;
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_HDR_RANDOM)
|
||||
std::mt19937 e;
|
||||
|
||||
void shuffle_view()
|
||||
{
|
||||
std::shuffle(dv.begin(),dv.end(),e);
|
||||
}
|
||||
#else
|
||||
/* for pre-C++11 compilers we use std::random_shuffle */
|
||||
|
||||
void shuffle_view()
|
||||
{
|
||||
std::random_shuffle(dv.begin(),dv.end());
|
||||
}
|
||||
#endif
|
||||
};
|
||||
|
||||
/* Repeat a given shuffling algorithm repeats_num times
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,54 @@
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_ACCESS_SPECIFIER_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_ACCESS_SPECIFIER_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp>
|
||||
#include <boost/detail/workaround.hpp>
|
||||
|
||||
/* In those compilers that do not accept the member template friend syntax,
|
||||
* some protected and private sections might need to be specified as
|
||||
* public.
|
||||
*/
|
||||
|
||||
#if defined(BOOST_NO_MEMBER_TEMPLATE_FRIENDS)
|
||||
#define BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS public
|
||||
#define BOOST_MULTI_INDEX_PRIVATE_IF_MEMBER_TEMPLATE_FRIENDS public
|
||||
#else
|
||||
#define BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS protected
|
||||
#define BOOST_MULTI_INDEX_PRIVATE_IF_MEMBER_TEMPLATE_FRIENDS private
|
||||
#endif
|
||||
|
||||
/* GCC does not correctly support in-class using declarations for template
|
||||
* functions. See http://gcc.gnu.org/bugzilla/show_bug.cgi?id=9810
|
||||
* MSVC 7.1/8.0 seem to have a similar problem, though the conditions in
|
||||
* which the error happens are not that simple. I have yet to isolate this
|
||||
* into a snippet suitable for bug reporting.
|
||||
* Sun Studio also has this problem, which might be related, from the
|
||||
* information gathered at Sun forums, with a known issue notified at the
|
||||
* internal bug report 6421933. The bug is present up to Studio Express 2,
|
||||
* the latest preview version of the future Sun Studio 12. As of this writing
|
||||
* (October 2006) it is not known whether a fix will finally make it into the
|
||||
* official Sun Studio 12.
|
||||
*/
|
||||
|
||||
#if BOOST_WORKAROUND(__GNUC__,==3)&&(__GNUC_MINOR__<4)||\
|
||||
BOOST_WORKAROUND(BOOST_MSVC,==1310)||\
|
||||
BOOST_WORKAROUND(BOOST_MSVC,==1400)||\
|
||||
BOOST_WORKAROUND(__SUNPRO_CC,BOOST_TESTED_AT(0x590))
|
||||
#define BOOST_MULTI_INDEX_PRIVATE_IF_USING_DECL_FOR_TEMPL_FUNCTIONS public
|
||||
#else
|
||||
#define BOOST_MULTI_INDEX_PRIVATE_IF_USING_DECL_FOR_TEMPL_FUNCTIONS private
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -25,8 +25,14 @@ namespace detail{
|
||||
template<typename T>
|
||||
void adl_swap(T& x,T& y)
|
||||
{
|
||||
|
||||
#if !defined(BOOST_FUNCTION_SCOPE_USING_DECLARATION_BREAKS_ADL)
|
||||
using std::swap;
|
||||
swap(x,y);
|
||||
#else
|
||||
std::swap(x,y);
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
@@ -0,0 +1,143 @@
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_ALLOCATOR_TRAITS_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_ALLOCATOR_TRAITS_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_ALLOCATOR)
|
||||
#include <memory>
|
||||
#else
|
||||
#include <boost/detail/workaround.hpp>
|
||||
#include <boost/move/core.hpp>
|
||||
#include <boost/move/utility_core.hpp>
|
||||
#include <boost/multi_index/detail/vartempl_support.hpp>
|
||||
#include <new>
|
||||
#endif
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* poor man's replacement of std::allocator_traits */
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_ALLOCATOR)
|
||||
|
||||
template<typename Allocator>
|
||||
struct allocator_traits:std::allocator_traits<Allocator>
|
||||
{
|
||||
/* wrap std::allocator_traits alias templates for use in C++03 codebase */
|
||||
|
||||
typedef std::allocator_traits<Allocator> super;
|
||||
|
||||
template<typename T>
|
||||
struct rebind_alloc
|
||||
{
|
||||
typedef typename super::template rebind_alloc<T> type;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
struct rebind_traits
|
||||
{
|
||||
typedef typename super::template rebind_traits<T> type;
|
||||
};
|
||||
};
|
||||
|
||||
#else
|
||||
|
||||
/* not a full std::allocator_traits rewrite (not needed) */
|
||||
|
||||
template<typename Allocator>
|
||||
struct allocator_traits
|
||||
{
|
||||
typedef Allocator allocator_type;
|
||||
typedef typename Allocator::value_type value_type;
|
||||
typedef typename Allocator::pointer pointer;
|
||||
typedef typename Allocator::const_pointer const_pointer;
|
||||
|
||||
/* [const_]void_pointer not provided as boost::pointer_traits's
|
||||
* rebind_to has been seen to fail with things like
|
||||
* boost::interprocess::offset_ptr in relatively old environments.
|
||||
*/
|
||||
|
||||
typedef typename Allocator::difference_type difference_type;
|
||||
typedef typename Allocator::size_type size_type;
|
||||
|
||||
template<typename T>
|
||||
struct rebind_alloc
|
||||
{
|
||||
typedef typename Allocator::template rebind<T>::other type;
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
struct rebind_traits
|
||||
{
|
||||
typedef allocator_traits<typename rebind_alloc<T>::type> type;
|
||||
};
|
||||
|
||||
static pointer allocate(Allocator& a,size_type n){return a.allocate(n);}
|
||||
static pointer allocate(Allocator& a,size_type n,const_pointer p)
|
||||
/* should've been const_void_pointer p */
|
||||
{return a.allocate(n,p);}
|
||||
static void deallocate(Allocator& a,pointer p,size_type n)
|
||||
{a.deallocate(p,n);}
|
||||
template<typename T>
|
||||
static void construct(Allocator&,T* p,const T& x)
|
||||
{::new (static_cast<void*>(p)) T(x);}
|
||||
template<typename T>
|
||||
static void construct(Allocator&,T* p,BOOST_RV_REF(T) x)
|
||||
{::new (static_cast<void*>(p)) T(boost::move(x));}
|
||||
|
||||
template<typename T,BOOST_MULTI_INDEX_TEMPLATE_PARAM_PACK>
|
||||
static void construct(Allocator&,T* p,BOOST_MULTI_INDEX_FUNCTION_PARAM_PACK)
|
||||
{
|
||||
vartempl_placement_new(p,BOOST_MULTI_INDEX_FORWARD_PARAM_PACK);
|
||||
}
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC,BOOST_TESTED_AT(1500))
|
||||
/* MSVC issues spurious warnings about unreferencend formal parameters in
|
||||
* destroy<T> when T is a class with trivial dtor.
|
||||
*/
|
||||
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4100)
|
||||
#endif
|
||||
|
||||
template<typename T>
|
||||
static void destroy(Allocator&,T* p){p->~T();}
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC,BOOST_TESTED_AT(1500))
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
static size_type max_size(Allocator& a)BOOST_NOEXCEPT{return a.max_size();}
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
template<typename Allocator,typename T>
|
||||
struct rebind_alloc_for
|
||||
{
|
||||
typedef typename allocator_traits<Allocator>::
|
||||
template rebind_alloc<T>::type type;
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,76 +0,0 @@
|
||||
/* Copyright 2003-2021 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_ANY_CONTAINER_VIEW_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_ANY_CONTAINER_VIEW_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* type-erased, non-owning view over a ConstIterator-container's range */
|
||||
|
||||
template<typename ConstIterator>
|
||||
class any_container_view
|
||||
{
|
||||
public:
|
||||
template<typename Container>
|
||||
any_container_view(const Container& x):px(&x),pt(vtable_for<Container>()){}
|
||||
|
||||
const void* container()const{return px;}
|
||||
ConstIterator begin()const{return pt->begin(px);}
|
||||
ConstIterator end()const{return pt->end(px);}
|
||||
|
||||
private:
|
||||
struct vtable
|
||||
{
|
||||
ConstIterator (*begin)(const void*);
|
||||
ConstIterator (*end)(const void*);
|
||||
};
|
||||
|
||||
template<typename Container>
|
||||
static ConstIterator begin_for(const void* px)
|
||||
{
|
||||
return static_cast<const Container*>(px)->begin();
|
||||
}
|
||||
|
||||
template<typename Container>
|
||||
static ConstIterator end_for(const void* px)
|
||||
{
|
||||
return static_cast<const Container*>(px)->end();
|
||||
}
|
||||
|
||||
template<typename Container>
|
||||
vtable* vtable_for()
|
||||
{
|
||||
static vtable v=
|
||||
{
|
||||
&begin_for<Container>,
|
||||
&end_for<Container>
|
||||
};
|
||||
|
||||
return &v;
|
||||
}
|
||||
|
||||
const void* px;
|
||||
vtable* pt;
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2023 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2016 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,9 +14,9 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/no_exceptions_support.hpp>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/detail/no_exceptions_support.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
#include <boost/serialization/serialization.hpp>
|
||||
#include <boost/type_traits/aligned_storage.hpp>
|
||||
#include <boost/type_traits/alignment_of.hpp>
|
||||
|
||||
@@ -34,7 +34,7 @@ struct archive_constructed:private noncopyable
|
||||
template<class Archive>
|
||||
archive_constructed(Archive& ar,const unsigned int version)
|
||||
{
|
||||
core::load_construct_data_adl(ar,&get(),version);
|
||||
serialization::load_construct_data_adl(ar,&get(),version);
|
||||
BOOST_TRY{
|
||||
ar>>get();
|
||||
}
|
||||
@@ -48,9 +48,9 @@ struct archive_constructed:private noncopyable
|
||||
template<class Archive>
|
||||
archive_constructed(const char* name,Archive& ar,const unsigned int version)
|
||||
{
|
||||
core::load_construct_data_adl(ar,&get(),version);
|
||||
serialization::load_construct_data_adl(ar,&get(),version);
|
||||
BOOST_TRY{
|
||||
ar>>core::make_nvp(name,get());
|
||||
ar>>serialization::make_nvp(name,get());
|
||||
}
|
||||
BOOST_CATCH(...){
|
||||
(&get())->~T();
|
||||
|
||||
@@ -1,129 +0,0 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_AUGMENTED_STDTUPLE_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_AUGMENTED_STDTUPLE_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/algorithm.hpp>
|
||||
#include <boost/mp11/function.hpp>
|
||||
#include <boost/mp11/list.hpp>
|
||||
#include <boost/mp11/integer_sequence.hpp>
|
||||
#include <boost/mp11/integral.hpp>
|
||||
#include <boost/tuple/tuple.hpp>
|
||||
#include <tuple>
|
||||
#include <type_traits>
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* augmented_stdtuple<Ts...> derives from std::tuple<Ts...> and provides the
|
||||
* following non-standard constructors:
|
||||
*
|
||||
* - augmented_stdtuple(const Ts& = Ts()...) (this signature is not legal C++,
|
||||
* shown for explanatory purposes).
|
||||
* - augmented_stdtuple(boost::tuple<Ts...>) if sizeof...(Ts) does not exceed
|
||||
* the maximum length of a boost::tuple (10 as of this writing).
|
||||
*/
|
||||
|
||||
template<typename T,typename U>
|
||||
using is_convertible_to_cref=std::is_convertible<T,const U&>;
|
||||
|
||||
template<typename FromList,typename ToList,typename=void>
|
||||
struct are_convertible_to_crefs:mp11::mp_false{};
|
||||
|
||||
template<typename FromList,typename ToList>
|
||||
struct are_convertible_to_crefs<
|
||||
FromList,ToList,
|
||||
typename std::enable_if<
|
||||
(mp11::mp_size<FromList>::value<=mp11::mp_size<ToList>::value)
|
||||
>::type
|
||||
>:
|
||||
mp11::mp_apply<
|
||||
mp11::mp_and,
|
||||
mp11::mp_transform<
|
||||
is_convertible_to_cref,
|
||||
FromList,
|
||||
mp11::mp_take_c<ToList,mp11::mp_size<FromList>::value>
|
||||
>
|
||||
>
|
||||
{};
|
||||
|
||||
template<typename... Ts>
|
||||
struct augmented_stdtuple:std::tuple<Ts...>
|
||||
{
|
||||
private:
|
||||
using super=std::tuple<Ts...>;
|
||||
static constexpr std::size_t N=sizeof...(Ts);
|
||||
|
||||
template<typename... Args>
|
||||
using are_convertible_to_crefs=
|
||||
typename detail::are_convertible_to_crefs<mp11::mp_list<Args...>,super>;
|
||||
|
||||
struct boost_tuple_too_short{};
|
||||
using boost_tuple_arg=mp11::mp_eval_if_c<
|
||||
(mp11::mp_size<boost::tuple<>>::value < N),
|
||||
boost_tuple_too_short,
|
||||
boost::tuple,Ts...
|
||||
>;
|
||||
|
||||
struct full_args_ctor{};
|
||||
augmented_stdtuple(full_args_ctor,const Ts&... args):super(args...){}
|
||||
|
||||
struct partial_args_ctor{};
|
||||
template<std::size_t... Is,typename... Args>
|
||||
augmented_stdtuple(
|
||||
partial_args_ctor,mp11::index_sequence<Is...>,Args&&... args):
|
||||
augmented_stdtuple(
|
||||
full_args_ctor{},
|
||||
std::forward<Args>(args)...,
|
||||
typename std::tuple_element<sizeof...(Args)+Is,super>::type()...)
|
||||
{}
|
||||
|
||||
struct boost_tuple_ctor{};
|
||||
template<std::size_t... Is>
|
||||
augmented_stdtuple(
|
||||
boost_tuple_ctor,mp11::index_sequence<Is...>,const boost_tuple_arg& x):
|
||||
super(tuples::get<Is>(x)...)
|
||||
{}
|
||||
|
||||
public:
|
||||
template<
|
||||
typename... Args,
|
||||
typename std::enable_if<
|
||||
are_convertible_to_crefs<Args&&...>::value
|
||||
>::type* =nullptr
|
||||
>
|
||||
augmented_stdtuple(Args&&... args):
|
||||
augmented_stdtuple(
|
||||
partial_args_ctor(),mp11::make_index_sequence<N-sizeof...(Args)>(),
|
||||
std::forward<Args>(args)...)
|
||||
{}
|
||||
|
||||
augmented_stdtuple(const super& x):super(x){}
|
||||
|
||||
augmented_stdtuple(const boost_tuple_arg& x):
|
||||
augmented_stdtuple(
|
||||
boost_tuple_ctor(),mp11::make_index_sequence<N>(),x)
|
||||
{}
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,10 +15,9 @@
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <algorithm>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <boost/multi_index/detail/adl_swap.hpp>
|
||||
#include <boost/type_traits/integral_constant.hpp>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
#include <memory>
|
||||
|
||||
namespace boost{
|
||||
@@ -46,15 +45,18 @@ namespace detail{
|
||||
template<typename T,typename Allocator=std::allocator<T> >
|
||||
struct auto_space:private noncopyable
|
||||
{
|
||||
typedef allocator_rebind_t<Allocator,T> allocator;
|
||||
typedef allocator_pointer_t<allocator> pointer;
|
||||
typedef allocator_size_type_t<allocator> size_type;
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,T>
|
||||
::type allocator;
|
||||
typedef allocator_traits<allocator> alloc_traits;
|
||||
typedef typename alloc_traits::pointer pointer;
|
||||
typedef typename alloc_traits::size_type size_type;
|
||||
|
||||
explicit auto_space(const Allocator& al=Allocator(),size_type n=1):
|
||||
al_(al),n_(n),data_(n_?allocator_allocate(al_,n_):pointer(0))
|
||||
al_(al),n_(n),data_(n_?alloc_traits::allocate(al_,n_):pointer(0))
|
||||
{}
|
||||
|
||||
~auto_space(){if(n_)allocator_deallocate(al_,data_,n_);}
|
||||
~auto_space(){if(n_)alloc_traits::deallocate(al_,data_,n_);}
|
||||
|
||||
Allocator get_allocator()const{return al_;}
|
||||
|
||||
@@ -62,26 +64,11 @@ struct auto_space:private noncopyable
|
||||
|
||||
void swap(auto_space& x)
|
||||
{
|
||||
swap(
|
||||
x,
|
||||
boost::integral_constant<
|
||||
bool,
|
||||
allocator_propagate_on_container_swap_t<allocator>::value>());
|
||||
}
|
||||
|
||||
void swap(auto_space& x,boost::true_type /* swap_allocators */)
|
||||
{
|
||||
adl_swap(al_,x.al_);
|
||||
if(al_!=x.al_)adl_swap(al_,x.al_);
|
||||
std::swap(n_,x.n_);
|
||||
std::swap(data_,x.data_);
|
||||
}
|
||||
|
||||
void swap(auto_space& x,boost::false_type /* swap_allocators */)
|
||||
{
|
||||
std::swap(n_,x.n_);
|
||||
std::swap(data_,x.data_);
|
||||
}
|
||||
|
||||
private:
|
||||
allocator al_;
|
||||
size_type n_;
|
||||
|
||||
@@ -1,36 +0,0 @@
|
||||
/* Copyright 2003-2023 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_BAD_ARCHIVE_EXCEPTION_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_BAD_ARCHIVE_EXCEPTION_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <stdexcept>
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
struct bad_archive_exception:std::runtime_error
|
||||
{
|
||||
bad_archive_exception():std::runtime_error("Invalid or corrupted archive"){}
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,9 +14,10 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/integral.hpp>
|
||||
#include <boost/mp11/list.hpp>
|
||||
#include <boost/mp11/utility.hpp>
|
||||
#include <boost/detail/workaround.hpp>
|
||||
#include <boost/mpl/at.hpp>
|
||||
#include <boost/mpl/apply.hpp>
|
||||
#include <boost/mpl/size.hpp>
|
||||
#include <boost/multi_index/detail/index_base.hpp>
|
||||
#include <boost/multi_index/detail/is_index_list.hpp>
|
||||
#include <boost/static_assert.hpp>
|
||||
@@ -27,31 +28,39 @@ namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* Mp11 machinery to construct a linear hierarchy of indices out of
|
||||
* an index list.
|
||||
/* MPL machinery to construct a linear hierarchy of indices out of
|
||||
* a index list.
|
||||
*/
|
||||
|
||||
template<typename N,typename Mp11IndexSpecifierList,typename SuperMeta>
|
||||
using nth_layer_index=typename mp11::mp_at<Mp11IndexSpecifierList,N>::
|
||||
template index_class<SuperMeta>::type;
|
||||
struct index_applier
|
||||
{
|
||||
template<typename IndexSpecifierMeta,typename SuperMeta>
|
||||
struct apply
|
||||
{
|
||||
typedef typename IndexSpecifierMeta::type index_specifier;
|
||||
typedef typename index_specifier::
|
||||
BOOST_NESTED_TEMPLATE index_class<SuperMeta>::type type;
|
||||
};
|
||||
};
|
||||
|
||||
template<int N,typename Value,typename IndexSpecifierList,typename Allocator>
|
||||
struct nth_layer
|
||||
{
|
||||
using Mp11IndexSpecifierList=detail::mp11_index_list<IndexSpecifierList>;
|
||||
using type=mp11::mp_eval_if_c<
|
||||
N==mp11::mp_size<Mp11IndexSpecifierList>::value,
|
||||
index_base<Value,IndexSpecifierList,Allocator>,
|
||||
nth_layer_index,
|
||||
mp11::mp_int<N>,
|
||||
Mp11IndexSpecifierList,
|
||||
nth_layer<N+1,Value,IndexSpecifierList,Allocator>
|
||||
>;
|
||||
BOOST_STATIC_CONSTANT(int,length=mpl::size<IndexSpecifierList>::value);
|
||||
|
||||
typedef typename mpl::eval_if_c<
|
||||
N==length,
|
||||
mpl::identity<index_base<Value,IndexSpecifierList,Allocator> >,
|
||||
mpl::apply2<
|
||||
index_applier,
|
||||
mpl::at_c<IndexSpecifierList,N>,
|
||||
nth_layer<N+1,Value,IndexSpecifierList,Allocator>
|
||||
>
|
||||
>::type type;
|
||||
};
|
||||
|
||||
template<typename Value,typename IndexSpecifierList,typename Allocator>
|
||||
struct multi_index_base_type:
|
||||
nth_layer<0,Value,IndexSpecifierList,Allocator>
|
||||
struct multi_index_base_type:nth_layer<0,Value,IndexSpecifierList,Allocator>
|
||||
{
|
||||
BOOST_STATIC_ASSERT(detail::is_index_list<IndexSpecifierList>::value);
|
||||
};
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,11 +14,11 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
#include <boost/operators.hpp>
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/serialization/nvp.hpp>
|
||||
#include <boost/serialization/split_member.hpp>
|
||||
#endif
|
||||
|
||||
namespace boost{
|
||||
@@ -67,27 +67,23 @@ public:
|
||||
* see explanation in safe_mode_iterator notes in safe_mode.hpp.
|
||||
*/
|
||||
|
||||
template<class Archive>
|
||||
void serialize(Archive& ar,const unsigned int version)
|
||||
{
|
||||
core::split_member(ar,*this,version);
|
||||
}
|
||||
BOOST_SERIALIZATION_SPLIT_MEMBER()
|
||||
|
||||
typedef typename Node::base_type node_base_type;
|
||||
|
||||
template<class Archive>
|
||||
void save(Archive& ar,const unsigned int)const
|
||||
{
|
||||
node_base_type* bnode=get_node();
|
||||
ar<<core::make_nvp("pointer",bnode);
|
||||
node_base_type* bnode=node;
|
||||
ar<<serialization::make_nvp("pointer",bnode);
|
||||
}
|
||||
|
||||
template<class Archive>
|
||||
void load(Archive& ar,const unsigned int)
|
||||
{
|
||||
node_base_type* bnode;
|
||||
ar>>core::make_nvp("pointer",bnode);
|
||||
node=typename Node::pointer(static_cast<Node*>(bnode));
|
||||
ar>>serialization::make_nvp("pointer",bnode);
|
||||
node=static_cast<Node*>(bnode);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -95,10 +91,10 @@ public:
|
||||
|
||||
typedef Node node_type;
|
||||
|
||||
Node* get_node()const{return raw_ptr<Node*>(node);}
|
||||
Node* get_node()const{return node;}
|
||||
|
||||
private:
|
||||
typename Node::pointer node;
|
||||
Node* node;
|
||||
};
|
||||
|
||||
template<typename Node>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,10 +15,10 @@
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <algorithm>
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/auto_space.hpp>
|
||||
#include <boost/multi_index/detail/hash_index_node.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
#include <boost/preprocessor/repetition/repeat.hpp>
|
||||
#include <boost/preprocessor/seq/elem.hpp>
|
||||
#include <boost/preprocessor/seq/enum.hpp>
|
||||
@@ -27,8 +27,8 @@
|
||||
#include <limits.h>
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/multi_index/detail/bad_archive_exception.hpp>
|
||||
#include <boost/archive/archive_exception.hpp>
|
||||
#include <boost/serialization/access.hpp>
|
||||
#include <boost/throw_exception.hpp>
|
||||
#endif
|
||||
|
||||
@@ -129,10 +129,10 @@ class bucket_array:bucket_array_base<>
|
||||
{
|
||||
typedef bucket_array_base<> super;
|
||||
typedef hashed_index_base_node_impl<
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
Allocator,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
> base_node_impl_type;
|
||||
|
||||
public:
|
||||
@@ -173,13 +173,6 @@ public:
|
||||
spc.swap(x.spc);
|
||||
}
|
||||
|
||||
template<typename BoolConstant>
|
||||
void swap(bucket_array& x,BoolConstant swap_allocators)
|
||||
{
|
||||
std::swap(size_index_,x.size_index_);
|
||||
spc.swap(x.spc,swap_allocators);
|
||||
}
|
||||
|
||||
private:
|
||||
typedef auto_space<base_node_impl_type,Allocator> auto_space_type;
|
||||
typedef typename auto_space_type::size_type auto_space_size_type;
|
||||
@@ -224,19 +217,28 @@ void swap(bucket_array<Allocator>& x,bucket_array<Allocator>& y)
|
||||
* somehow invalid archive.
|
||||
*/
|
||||
|
||||
#if defined(BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP)
|
||||
namespace serialization{
|
||||
#else
|
||||
namespace multi_index{
|
||||
namespace detail{
|
||||
#endif
|
||||
|
||||
template<class Archive,typename Allocator>
|
||||
inline void load_construct_data(
|
||||
Archive&,boost::multi_index::detail::bucket_array<Allocator>*,
|
||||
const unsigned int)
|
||||
{
|
||||
throw_exception(boost::multi_index::detail::bad_archive_exception());
|
||||
throw_exception(
|
||||
archive::archive_exception(archive::archive_exception::other_exception));
|
||||
}
|
||||
|
||||
#if defined(BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP)
|
||||
} /* namespace serialization */
|
||||
#else
|
||||
} /* namespace multi_index::detail */
|
||||
} /* namespace multi_index */
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2014 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,7 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/utility.hpp>
|
||||
#include <boost/mpl/if.hpp>
|
||||
#include <boost/tuple/tuple.hpp>
|
||||
#include <tuple>
|
||||
|
||||
@@ -55,11 +55,11 @@ struct cons_stdtuple_ctor_normal
|
||||
|
||||
template<typename StdTuple,std::size_t N=0>
|
||||
struct cons_stdtuple_ctor:
|
||||
mp11::mp_if_c<
|
||||
boost::mpl::if_c<
|
||||
N<std::tuple_size<StdTuple>::value,
|
||||
cons_stdtuple_ctor_normal<StdTuple,N>,
|
||||
cons_stdtuple_ctor_terminal
|
||||
>
|
||||
>::type
|
||||
{};
|
||||
|
||||
template<typename StdTuple,std::size_t N>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2020 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -31,15 +31,13 @@ struct converter
|
||||
static Index& index(MultiIndexContainer& x){return x;}
|
||||
|
||||
static typename Index::const_iterator const_iterator(
|
||||
const MultiIndexContainer& x,
|
||||
typename MultiIndexContainer::final_node_type* node)
|
||||
const MultiIndexContainer& x,typename MultiIndexContainer::node_type* node)
|
||||
{
|
||||
return x.Index::make_iterator(node);
|
||||
}
|
||||
|
||||
static typename Index::iterator iterator(
|
||||
MultiIndexContainer& x,
|
||||
typename MultiIndexContainer::final_node_type* node)
|
||||
MultiIndexContainer& x,typename MultiIndexContainer::node_type* node)
|
||||
{
|
||||
return x.Index::make_iterator(node);
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -16,13 +16,12 @@
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <algorithm>
|
||||
#include <boost/core/addressof.hpp>
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <boost/core/no_exceptions_support.hpp>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/detail/no_exceptions_support.hpp>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/auto_space.hpp>
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
#include <functional>
|
||||
#include <utility>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -56,27 +55,18 @@ struct copy_map_entry
|
||||
}
|
||||
};
|
||||
|
||||
struct copy_map_value_copier
|
||||
{
|
||||
template<typename Value>
|
||||
const Value& operator()(Value& x)const{return x;}
|
||||
};
|
||||
|
||||
struct copy_map_value_mover
|
||||
{
|
||||
template<typename Value>
|
||||
Value&& operator()(Value& x)const{return std::move(x);}
|
||||
};
|
||||
|
||||
template <typename Node,typename Allocator>
|
||||
class copy_map:private noncopyable
|
||||
{
|
||||
typedef allocator_rebind_t<Allocator,Node> allocator_type;
|
||||
typedef allocator_pointer_t<allocator_type> pointer;
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,Node
|
||||
>::type allocator_type;
|
||||
typedef allocator_traits<allocator_type> alloc_traits;
|
||||
typedef typename alloc_traits::pointer pointer;
|
||||
|
||||
public:
|
||||
typedef const copy_map_entry<Node>* const_iterator;
|
||||
typedef allocator_size_type_t<allocator_type> size_type;
|
||||
typedef const copy_map_entry<Node>* const_iterator;
|
||||
typedef typename alloc_traits::size_type size_type;
|
||||
|
||||
copy_map(
|
||||
const Allocator& al,size_type size,Node* header_org,Node* header_cpy):
|
||||
@@ -88,7 +78,7 @@ public:
|
||||
{
|
||||
if(!released){
|
||||
for(size_type i=0;i<n;++i){
|
||||
allocator_destroy(
|
||||
alloc_traits::destroy(
|
||||
al_,boost::addressof((spc.data()+i)->second->value()));
|
||||
deallocate((spc.data()+i)->second);
|
||||
}
|
||||
@@ -98,8 +88,27 @@ public:
|
||||
const_iterator begin()const{return raw_ptr<const_iterator>(spc.data());}
|
||||
const_iterator end()const{return raw_ptr<const_iterator>(spc.data()+n);}
|
||||
|
||||
void copy_clone(Node* node){clone(node,copy_map_value_copier());}
|
||||
void move_clone(Node* node){clone(node,copy_map_value_mover());}
|
||||
void clone(Node* node)
|
||||
{
|
||||
(spc.data()+n)->first=node;
|
||||
(spc.data()+n)->second=raw_ptr<Node*>(allocate());
|
||||
BOOST_TRY{
|
||||
alloc_traits::construct(
|
||||
al_,boost::addressof((spc.data()+n)->second->value()),node->value());
|
||||
}
|
||||
BOOST_CATCH(...){
|
||||
deallocate((spc.data()+n)->second);
|
||||
BOOST_RETHROW;
|
||||
}
|
||||
BOOST_CATCH_END
|
||||
++n;
|
||||
|
||||
if(n==size_){
|
||||
std::sort(
|
||||
raw_ptr<copy_map_entry<Node>*>(spc.data()),
|
||||
raw_ptr<copy_map_entry<Node>*>(spc.data())+size_);
|
||||
}
|
||||
}
|
||||
|
||||
Node* find(Node* node)const
|
||||
{
|
||||
@@ -124,36 +133,12 @@ private:
|
||||
|
||||
pointer allocate()
|
||||
{
|
||||
return allocator_allocate(al_,1);
|
||||
return alloc_traits::allocate(al_,1);
|
||||
}
|
||||
|
||||
void deallocate(Node* node)
|
||||
{
|
||||
allocator_deallocate(al_,static_cast<pointer>(node),1);
|
||||
}
|
||||
|
||||
template<typename ValueAccess>
|
||||
void clone(Node* node,ValueAccess access)
|
||||
{
|
||||
(spc.data()+n)->first=node;
|
||||
(spc.data()+n)->second=raw_ptr<Node*>(allocate());
|
||||
BOOST_TRY{
|
||||
allocator_construct(
|
||||
al_,boost::addressof((spc.data()+n)->second->value()),
|
||||
access(node->value()));
|
||||
}
|
||||
BOOST_CATCH(...){
|
||||
deallocate((spc.data()+n)->second);
|
||||
BOOST_RETHROW;
|
||||
}
|
||||
BOOST_CATCH_END
|
||||
++n;
|
||||
|
||||
if(n==size_){
|
||||
std::sort(
|
||||
raw_ptr<copy_map_entry<Node>*>(spc.data()),
|
||||
raw_ptr<copy_map_entry<Node>*>(spc.data())+size_);
|
||||
}
|
||||
alloc_traits::deallocate(al_,static_cast<pointer>(node),1);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -1,34 +0,0 @@
|
||||
/* Copyright 2003-2022 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#if !defined(BOOST_CONFIG_HPP)
|
||||
#error <boost/config.hpp> must be included before this header
|
||||
#endif
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DETAIL_UNDEF_IF_CONSTEXPR_MACRO)
|
||||
|
||||
#if !defined(BOOST_NO_CXX17_IF_CONSTEXPR)
|
||||
#define BOOST_MULTI_INDEX_IF_CONSTEXPR if constexpr
|
||||
#else
|
||||
#define BOOST_MULTI_INDEX_IF_CONSTEXPR if
|
||||
#if defined(BOOST_MSVC)
|
||||
#define BOOST_MULTI_INDEX_DETAIL_C4127_DISABLED
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4127) /* conditional expression is constant */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#else
|
||||
|
||||
#undef BOOST_MULTI_INDEX_IF_CONSTEXPR
|
||||
#if defined(BOOST_MULTI_INDEX_DETAIL_C4127_DISABLED)
|
||||
#pragma warning(pop)
|
||||
#undef BOOST_MULTI_INDEX_DETAIL_C4127_DISABLED
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,7 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/algorithm.hpp>
|
||||
#include <boost/mpl/contains.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -28,7 +28,9 @@ template<typename Tag>
|
||||
struct has_tag
|
||||
{
|
||||
template<typename Index>
|
||||
using fn=mp11::mp_contains<typename Index::tag_list,Tag>;
|
||||
struct apply:mpl::contains<BOOST_DEDUCED_TYPENAME Index::tag_list,Tag>
|
||||
{
|
||||
};
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
@@ -37,4 +39,4 @@ struct has_tag
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,13 +14,15 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/container_hash/hash.hpp>
|
||||
#include <boost/mp11/utility.hpp>
|
||||
#include <boost/functional/hash.hpp>
|
||||
#include <boost/mpl/aux_/na.hpp>
|
||||
#include <boost/mpl/eval_if.hpp>
|
||||
#include <boost/mpl/identity.hpp>
|
||||
#include <boost/mpl/if.hpp>
|
||||
#include <boost/multi_index/tag.hpp>
|
||||
#include <boost/static_assert.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
#include <functional>
|
||||
#include <type_traits>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -44,44 +46,54 @@ namespace detail{
|
||||
* argument-dependent polymorphism.
|
||||
*/
|
||||
|
||||
template<typename KeyFromValue>
|
||||
struct index_args_default_hash
|
||||
{
|
||||
typedef ::boost::hash<typename KeyFromValue::result_type> type;
|
||||
};
|
||||
|
||||
template<typename KeyFromValue>
|
||||
struct index_args_default_pred
|
||||
{
|
||||
typedef std::equal_to<typename KeyFromValue::result_type> type;
|
||||
};
|
||||
|
||||
template<typename Arg1,typename Arg2,typename Arg3,typename Arg4>
|
||||
struct hashed_index_args
|
||||
{
|
||||
typedef is_tag<Arg1> full_form;
|
||||
|
||||
typedef mp11::mp_if<
|
||||
typedef typename mpl::if_<
|
||||
full_form,
|
||||
Arg1,
|
||||
tag< > > tag_list_type;
|
||||
typedef mp11::mp_if<
|
||||
tag< > >::type tag_list_type;
|
||||
typedef typename mpl::if_<
|
||||
full_form,
|
||||
Arg2,
|
||||
Arg1> key_from_value_type;
|
||||
typedef mp11::mp_if<
|
||||
Arg1>::type key_from_value_type;
|
||||
typedef typename mpl::if_<
|
||||
full_form,
|
||||
Arg3,
|
||||
Arg2> supplied_hash_type;
|
||||
typedef mp11::mp_eval_if_c<
|
||||
!std::is_void<supplied_hash_type>::value,
|
||||
supplied_hash_type,
|
||||
boost::hash,
|
||||
typename key_from_value_type::result_type
|
||||
> hash_type;
|
||||
typedef mp11::mp_if<
|
||||
Arg2>::type supplied_hash_type;
|
||||
typedef typename mpl::eval_if<
|
||||
mpl::is_na<supplied_hash_type>,
|
||||
index_args_default_hash<key_from_value_type>,
|
||||
mpl::identity<supplied_hash_type>
|
||||
>::type hash_type;
|
||||
typedef typename mpl::if_<
|
||||
full_form,
|
||||
Arg4,
|
||||
Arg3> supplied_pred_type;
|
||||
typedef mp11::mp_eval_if_c<
|
||||
!std::is_void<supplied_pred_type>::value,
|
||||
supplied_pred_type,
|
||||
std::equal_to,
|
||||
typename key_from_value_type::result_type
|
||||
> pred_type;
|
||||
Arg3>::type supplied_pred_type;
|
||||
typedef typename mpl::eval_if<
|
||||
mpl::is_na<supplied_pred_type>,
|
||||
index_args_default_pred<key_from_value_type>,
|
||||
mpl::identity<supplied_pred_type>
|
||||
>::type pred_type;
|
||||
|
||||
BOOST_STATIC_ASSERT(is_tag<tag_list_type>::value);
|
||||
BOOST_STATIC_ASSERT(!std::is_void<key_from_value_type>::value);
|
||||
BOOST_STATIC_ASSERT(!std::is_void<hash_type>::value);
|
||||
BOOST_STATIC_ASSERT(!std::is_void<pred_type>::value);
|
||||
BOOST_STATIC_ASSERT(!mpl::is_na<key_from_value_type>::value);
|
||||
BOOST_STATIC_ASSERT(!mpl::is_na<hash_type>::value);
|
||||
BOOST_STATIC_ASSERT(!mpl::is_na<pred_type>::value);
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,11 +14,12 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
#include <boost/operators.hpp>
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/serialization/nvp.hpp>
|
||||
#include <boost/serialization/split_member.hpp>
|
||||
#include <boost/serialization/version.hpp>
|
||||
#endif
|
||||
|
||||
namespace boost{
|
||||
@@ -33,13 +34,10 @@ namespace detail{
|
||||
struct hashed_index_global_iterator_tag{};
|
||||
struct hashed_index_local_iterator_tag{};
|
||||
|
||||
template<
|
||||
typename Node,typename BucketArray,
|
||||
typename IndexCategory,typename IteratorCategory
|
||||
>
|
||||
template<typename Node,typename BucketArray,typename Category>
|
||||
class hashed_index_iterator:
|
||||
public forward_iterator_helper<
|
||||
hashed_index_iterator<Node,BucketArray,IndexCategory,IteratorCategory>,
|
||||
hashed_index_iterator<Node,BucketArray,Category>,
|
||||
typename Node::value_type,
|
||||
typename Node::difference_type,
|
||||
const typename Node::value_type*,
|
||||
@@ -57,7 +55,7 @@ public:
|
||||
|
||||
hashed_index_iterator& operator++()
|
||||
{
|
||||
this->increment(IteratorCategory());
|
||||
this->increment(Category());
|
||||
return *this;
|
||||
}
|
||||
|
||||
@@ -66,25 +64,21 @@ public:
|
||||
* see explanation in safe_mode_iterator notes in safe_mode.hpp.
|
||||
*/
|
||||
|
||||
template<class Archive>
|
||||
void serialize(Archive& ar,const unsigned int version)
|
||||
{
|
||||
core::split_member(ar,*this,version);
|
||||
}
|
||||
BOOST_SERIALIZATION_SPLIT_MEMBER()
|
||||
|
||||
typedef typename Node::base_type node_base_type;
|
||||
|
||||
template<class Archive>
|
||||
void save(Archive& ar,const unsigned int)const
|
||||
{
|
||||
node_base_type* bnode=get_node();
|
||||
ar<<core::make_nvp("pointer",bnode);
|
||||
node_base_type* bnode=node;
|
||||
ar<<serialization::make_nvp("pointer",bnode);
|
||||
}
|
||||
|
||||
template<class Archive>
|
||||
void load(Archive& ar,const unsigned int version)
|
||||
{
|
||||
load(ar,version,IteratorCategory());
|
||||
load(ar,version,Category());
|
||||
}
|
||||
|
||||
template<class Archive>
|
||||
@@ -92,11 +86,11 @@ public:
|
||||
Archive& ar,const unsigned int version,hashed_index_global_iterator_tag)
|
||||
{
|
||||
node_base_type* bnode;
|
||||
ar>>core::make_nvp("pointer",bnode);
|
||||
node=typename Node::pointer(static_cast<Node*>(bnode));
|
||||
ar>>serialization::make_nvp("pointer",bnode);
|
||||
node=static_cast<Node*>(bnode);
|
||||
if(version<1){
|
||||
BucketArray* throw_away; /* consume unused ptr */
|
||||
ar>>core::make_nvp("pointer",throw_away);
|
||||
ar>>serialization::make_nvp("pointer",throw_away);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -105,14 +99,14 @@ public:
|
||||
Archive& ar,const unsigned int version,hashed_index_local_iterator_tag)
|
||||
{
|
||||
node_base_type* bnode;
|
||||
ar>>core::make_nvp("pointer",bnode);
|
||||
node=typename Node::pointer(static_cast<Node*>(bnode));
|
||||
ar>>serialization::make_nvp("pointer",bnode);
|
||||
node=static_cast<Node*>(bnode);
|
||||
if(version<1){
|
||||
BucketArray* buckets;
|
||||
ar>>core::make_nvp("pointer",buckets);
|
||||
if(buckets&&bnode&&node->impl()==buckets->end()->prior()){
|
||||
ar>>serialization::make_nvp("pointer",buckets);
|
||||
if(buckets&&node&&node->impl()==buckets->end()->prior()){
|
||||
/* end local_iterators used to point to end node, now they are null */
|
||||
node=typename Node::pointer(0);
|
||||
node=0;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -122,32 +116,27 @@ public:
|
||||
|
||||
typedef Node node_type;
|
||||
|
||||
Node* get_node()const{return raw_ptr<Node*>(node);}
|
||||
Node* get_node()const{return node;}
|
||||
|
||||
private:
|
||||
|
||||
void increment(hashed_index_global_iterator_tag)
|
||||
{
|
||||
Node::template increment<IndexCategory>(node);
|
||||
Node::increment(node);
|
||||
}
|
||||
|
||||
void increment(hashed_index_local_iterator_tag)
|
||||
{
|
||||
Node::template increment_local<IndexCategory>(node);
|
||||
Node::increment_local(node);
|
||||
}
|
||||
|
||||
typename Node::pointer node;
|
||||
Node* node;
|
||||
};
|
||||
|
||||
template<
|
||||
typename Node,typename BucketArray,
|
||||
typename IndexCategory,typename IteratorCategory
|
||||
>
|
||||
template<typename Node,typename BucketArray,typename Category>
|
||||
bool operator==(
|
||||
const hashed_index_iterator<
|
||||
Node,BucketArray,IndexCategory,IteratorCategory>& x,
|
||||
const hashed_index_iterator<
|
||||
Node,BucketArray,IndexCategory,IteratorCategory>& y)
|
||||
const hashed_index_iterator<Node,BucketArray,Category>& x,
|
||||
const hashed_index_iterator<Node,BucketArray,Category>& y)
|
||||
{
|
||||
return x.get_node()==y.get_node();
|
||||
}
|
||||
@@ -162,14 +151,9 @@ bool operator==(
|
||||
*/
|
||||
|
||||
namespace serialization {
|
||||
template<
|
||||
typename Node,typename BucketArray,
|
||||
typename IndexCategory,typename IteratorCategory
|
||||
>
|
||||
template<typename Node,typename BucketArray,typename Category>
|
||||
struct version<
|
||||
boost::multi_index::detail::hashed_index_iterator<
|
||||
Node,BucketArray,IndexCategory,IteratorCategory
|
||||
>
|
||||
boost::multi_index::detail::hashed_index_iterator<Node,BucketArray,Category>
|
||||
>
|
||||
{
|
||||
BOOST_STATIC_CONSTANT(int,value=1);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2019 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,7 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
#include <utility>
|
||||
|
||||
@@ -99,17 +99,19 @@ struct hashed_index_node_impl;
|
||||
template<typename Allocator>
|
||||
struct hashed_index_base_node_impl
|
||||
{
|
||||
typedef allocator_rebind_t<
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,hashed_index_base_node_impl
|
||||
> base_allocator;
|
||||
typedef allocator_rebind_t<
|
||||
>::type base_allocator;
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,hashed_index_node_impl<Allocator>
|
||||
> node_allocator;
|
||||
typedef allocator_pointer_t<base_allocator> base_pointer;
|
||||
typedef allocator_const_pointer_t<base_allocator> const_base_pointer;
|
||||
typedef allocator_pointer_t<node_allocator> pointer;
|
||||
typedef allocator_const_pointer_t<node_allocator> const_pointer;
|
||||
typedef allocator_difference_type_t<node_allocator> difference_type;
|
||||
>::type node_allocator;
|
||||
typedef allocator_traits<base_allocator> base_alloc_traits;
|
||||
typedef allocator_traits<node_allocator> node_alloc_traits;
|
||||
typedef typename base_alloc_traits::pointer base_pointer;
|
||||
typedef typename base_alloc_traits::const_pointer const_base_pointer;
|
||||
typedef typename node_alloc_traits::pointer pointer;
|
||||
typedef typename node_alloc_traits::const_pointer const_pointer;
|
||||
typedef typename node_alloc_traits::difference_type difference_type;
|
||||
|
||||
pointer& prior(){return prior_;}
|
||||
pointer prior()const{return prior_;}
|
||||
@@ -687,18 +689,18 @@ private:
|
||||
template<typename Super>
|
||||
struct hashed_index_node_trampoline:
|
||||
hashed_index_node_impl<
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
typename Super::allocator_type,char
|
||||
>
|
||||
>::type
|
||||
>
|
||||
{
|
||||
typedef allocator_rebind_t<
|
||||
typedef typename rebind_alloc_for<
|
||||
typename Super::allocator_type,char
|
||||
> impl_allocator_type;
|
||||
>::type impl_allocator_type;
|
||||
typedef hashed_index_node_impl<impl_allocator_type> impl_type;
|
||||
};
|
||||
|
||||
template<typename Super>
|
||||
template<typename Super,typename Category>
|
||||
struct hashed_index_node:
|
||||
Super,hashed_index_node_trampoline<Super>
|
||||
{
|
||||
@@ -707,23 +709,13 @@ private:
|
||||
|
||||
public:
|
||||
typedef typename trampoline::impl_type impl_type;
|
||||
typedef hashed_index_node_alg<
|
||||
impl_type,Category> node_alg;
|
||||
typedef typename trampoline::base_pointer impl_base_pointer;
|
||||
typedef typename trampoline::const_base_pointer const_impl_base_pointer;
|
||||
typedef typename trampoline::pointer impl_pointer;
|
||||
typedef typename trampoline::const_pointer const_impl_pointer;
|
||||
typedef typename trampoline::difference_type difference_type;
|
||||
typedef allocator_rebind_t<
|
||||
typename trampoline::impl_allocator_type,
|
||||
hashed_index_node> final_allocator_type;
|
||||
typedef allocator_pointer_t<
|
||||
final_allocator_type> pointer;
|
||||
typedef allocator_const_pointer_t<
|
||||
final_allocator_type> const_pointer;
|
||||
|
||||
template<typename Category>
|
||||
struct node_alg{
|
||||
typedef hashed_index_node_alg<impl_type,Category> type;
|
||||
};
|
||||
|
||||
impl_pointer& prior(){return trampoline::prior();}
|
||||
impl_pointer prior()const{return trampoline::prior();}
|
||||
@@ -760,16 +752,14 @@ public:
|
||||
|
||||
/* interoperability with hashed_index_iterator */
|
||||
|
||||
template<typename Category>
|
||||
static void increment(pointer& x)
|
||||
static void increment(hashed_index_node*& x)
|
||||
{
|
||||
x=pointer(from_impl(node_alg<Category>::type::after(x->impl())));
|
||||
x=from_impl(node_alg::after(x->impl()));
|
||||
}
|
||||
|
||||
template<typename Category>
|
||||
static void increment_local(pointer& x)
|
||||
static void increment_local(hashed_index_node*& x)
|
||||
{
|
||||
x=pointer(from_impl(node_alg<Category>::type::after_local(x->impl())));
|
||||
x=from_impl(node_alg::after_local(x->impl()));
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2022 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2008 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -13,7 +13,7 @@
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
|
||||
@@ -1,77 +0,0 @@
|
||||
/* Copyright 2003-2021 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_INDEX_ACCESS_SEQUENCE_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_INDEX_ACCESS_SEQUENCE_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/list.hpp>
|
||||
#include <boost/mp11/utility.hpp>
|
||||
#include <boost/multi_index_container_fwd.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* Successive access to the indices of a multi_index_container. Used as dst in
|
||||
* backbone function extract_(x,dst) to retrieve the destination indices
|
||||
* where iterators referring to x must be transferred to (in merging
|
||||
* operations).
|
||||
*/
|
||||
|
||||
template<typename MultiIndexContainer,int N=0>
|
||||
struct index_access_sequence;
|
||||
|
||||
struct index_access_sequence_terminal
|
||||
{
|
||||
index_access_sequence_terminal(void*){}
|
||||
};
|
||||
|
||||
template<typename MultiIndexContainer,int N>
|
||||
struct index_access_sequence_normal
|
||||
{
|
||||
MultiIndexContainer* p;
|
||||
|
||||
index_access_sequence_normal(MultiIndexContainer* p_):p(p_){}
|
||||
|
||||
typename nth_index<MultiIndexContainer,N>::type&
|
||||
get(){return p->template get<N>();}
|
||||
|
||||
index_access_sequence<MultiIndexContainer,N+1>
|
||||
next(){return index_access_sequence<MultiIndexContainer,N+1>(p);}
|
||||
};
|
||||
|
||||
template<typename MultiIndexContainer,int N>
|
||||
using index_access_sequence_base=mp11::mp_if_c<
|
||||
N<mp11::mp_size<typename MultiIndexContainer::index_type_list>::value,
|
||||
index_access_sequence_normal<MultiIndexContainer,N>,
|
||||
index_access_sequence_terminal
|
||||
>;
|
||||
|
||||
template<typename MultiIndexContainer,int N>
|
||||
struct index_access_sequence:index_access_sequence_base<MultiIndexContainer,N>
|
||||
{
|
||||
typedef index_access_sequence_base<
|
||||
MultiIndexContainer,N> super;
|
||||
|
||||
index_access_sequence(MultiIndexContainer* p):super(p){}
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,14 +15,16 @@
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/addressof.hpp>
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <boost/core/no_exceptions_support.hpp>
|
||||
#include <boost/detail/no_exceptions_support.hpp>
|
||||
#include <boost/detail/workaround.hpp>
|
||||
#include <boost/move/core.hpp>
|
||||
#include <boost/move/utility_core.hpp>
|
||||
#include <boost/mpl/vector.hpp>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/copy_map.hpp>
|
||||
#include <boost/multi_index/detail/do_not_copy_elements_tag.hpp>
|
||||
#include <boost/multi_index/detail/index_access_sequence.hpp>
|
||||
#include <boost/multi_index/detail/node_handle.hpp>
|
||||
#include <boost/multi_index/detail/node_type.hpp>
|
||||
#include <boost/multi_index/detail/type_list.hpp>
|
||||
#include <boost/multi_index/detail/vartempl_support.hpp>
|
||||
#include <boost/multi_index_container_fwd.hpp>
|
||||
#include <boost/tuple/tuple.hpp>
|
||||
#include <utility>
|
||||
@@ -54,47 +56,42 @@ template<typename Value,typename IndexSpecifierList,typename Allocator>
|
||||
class index_base
|
||||
{
|
||||
protected:
|
||||
typedef index_node_base<Value,Allocator> index_node_type;
|
||||
typedef index_node_base<Value,Allocator> node_type;
|
||||
typedef typename multi_index_node_type<
|
||||
Value,IndexSpecifierList,Allocator>::type final_node_type;
|
||||
typedef multi_index_container<
|
||||
Value,IndexSpecifierList,Allocator> final_type;
|
||||
typedef tuples::null_type ctor_args_list;
|
||||
typedef Allocator final_allocator_type;
|
||||
typedef node_handle<
|
||||
final_node_type,final_allocator_type> final_node_handle_type;
|
||||
typedef empty_type_list index_type_list;
|
||||
typedef empty_type_list iterator_type_list;
|
||||
typedef empty_type_list const_iterator_type_list;
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,typename Allocator::value_type
|
||||
>::type final_allocator_type;
|
||||
typedef mpl::vector0<> index_type_list;
|
||||
typedef mpl::vector0<> iterator_type_list;
|
||||
typedef mpl::vector0<> const_iterator_type_list;
|
||||
typedef copy_map<
|
||||
final_node_type,
|
||||
final_allocator_type> copy_map_type;
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
typedef index_saver<
|
||||
index_node_type,
|
||||
node_type,
|
||||
final_allocator_type> index_saver_type;
|
||||
typedef index_loader<
|
||||
index_node_type,
|
||||
node_type,
|
||||
final_node_type,
|
||||
final_allocator_type> index_loader_type;
|
||||
#endif
|
||||
|
||||
private:
|
||||
typedef Value value_type;
|
||||
typedef allocator_size_type_t<Allocator> size_type;
|
||||
typedef allocator_traits<Allocator> alloc_traits;
|
||||
typedef typename alloc_traits::size_type size_type;
|
||||
|
||||
protected:
|
||||
explicit index_base(
|
||||
const ctor_args_list&,const Allocator&,index_node_type*){}
|
||||
explicit index_base(const ctor_args_list&,const Allocator&){}
|
||||
|
||||
index_base(
|
||||
const index_base<Value,IndexSpecifierList,Allocator>&,
|
||||
const Allocator&,index_node_type*){}
|
||||
|
||||
index_base(
|
||||
const index_base<Value,IndexSpecifierList,Allocator>&,
|
||||
const Allocator&,index_node_type*,
|
||||
do_not_copy_elements_tag)
|
||||
{}
|
||||
|
||||
@@ -120,7 +117,7 @@ protected:
|
||||
{
|
||||
x=final().allocate_node();
|
||||
BOOST_TRY{
|
||||
final().construct_value(x,std::move(const_cast<value_type&>(v)));
|
||||
final().construct_value(x,boost::move(const_cast<value_type&>(v)));
|
||||
}
|
||||
BOOST_CATCH(...){
|
||||
final().deallocate_node(x);
|
||||
@@ -135,63 +132,57 @@ protected:
|
||||
return x;
|
||||
}
|
||||
|
||||
template<typename MultiIndexContainer>
|
||||
final_node_type* insert_(
|
||||
const value_type&,final_node_type*& x,MultiIndexContainer* p)
|
||||
{
|
||||
p->final_extract_for_transfer_(
|
||||
x,index_access_sequence<final_type>(&final()));
|
||||
return x;
|
||||
}
|
||||
|
||||
final_node_type* insert_(
|
||||
const value_type& v,index_node_type*,final_node_type*& x,lvalue_tag)
|
||||
const value_type& v,node_type*,final_node_type*& x,lvalue_tag)
|
||||
{
|
||||
return insert_(v,x,lvalue_tag());
|
||||
}
|
||||
|
||||
final_node_type* insert_(
|
||||
const value_type& v,index_node_type*,final_node_type*& x,rvalue_tag)
|
||||
const value_type& v,node_type*,final_node_type*& x,rvalue_tag)
|
||||
{
|
||||
return insert_(v,x,rvalue_tag());
|
||||
}
|
||||
|
||||
final_node_type* insert_(
|
||||
const value_type&,index_node_type*,final_node_type*& x,emplaced_tag)
|
||||
const value_type&,node_type*,final_node_type*& x,emplaced_tag)
|
||||
{
|
||||
return x;
|
||||
}
|
||||
|
||||
template<typename Dst>
|
||||
void extract_(index_node_type*,Dst){}
|
||||
void erase_(node_type* x)
|
||||
{
|
||||
final().destroy_value(static_cast<final_node_type*>(x));
|
||||
}
|
||||
|
||||
void delete_node_(node_type* x)
|
||||
{
|
||||
final().destroy_value(static_cast<final_node_type*>(x));
|
||||
}
|
||||
|
||||
void clear_(){}
|
||||
|
||||
template<typename BoolConstant>
|
||||
void swap_(
|
||||
index_base<Value,IndexSpecifierList,Allocator>&,
|
||||
BoolConstant /* swap_allocators */)
|
||||
{}
|
||||
void swap_(index_base<Value,IndexSpecifierList,Allocator>&){}
|
||||
|
||||
void swap_elements_(index_base<Value,IndexSpecifierList,Allocator>&){}
|
||||
|
||||
bool replace_(const value_type& v,index_node_type* x,lvalue_tag)
|
||||
bool replace_(const value_type& v,node_type* x,lvalue_tag)
|
||||
{
|
||||
x->value()=v;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool replace_(const value_type& v,index_node_type* x,rvalue_tag)
|
||||
bool replace_(const value_type& v,node_type* x,rvalue_tag)
|
||||
{
|
||||
x->value()=std::move(const_cast<value_type&>(v));
|
||||
x->value()=boost::move(const_cast<value_type&>(v));
|
||||
return true;
|
||||
}
|
||||
|
||||
bool modify_(index_node_type*){return true;}
|
||||
bool modify_(node_type*){return true;}
|
||||
|
||||
bool modify_rollback_(index_node_type*){return true;}
|
||||
bool modify_rollback_(node_type*){return true;}
|
||||
|
||||
bool check_rollback_(index_node_type*)const{return true;}
|
||||
bool check_rollback_(node_type*)const{return true;}
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
/* serialization */
|
||||
@@ -214,10 +205,6 @@ protected:
|
||||
final_type& final(){return *static_cast<final_type*>(this);}
|
||||
const final_type& final()const{return *static_cast<const final_type*>(this);}
|
||||
|
||||
template<typename Index>
|
||||
static typename Index::final_type& final(Index& x) /* cross-index access */
|
||||
{return static_cast<typename Index::final_type&>(x);}
|
||||
|
||||
final_node_type* final_header()const{return final().header();}
|
||||
|
||||
bool final_empty_()const{return final().empty_();}
|
||||
@@ -234,17 +221,12 @@ protected:
|
||||
template<typename T>
|
||||
std::pair<final_node_type*,bool> final_insert_ref_(T& t)
|
||||
{return final().insert_ref_(t);}
|
||||
std::pair<final_node_type*,bool> final_insert_nh_(final_node_handle_type& nh)
|
||||
{return final().insert_nh_(nh);}
|
||||
|
||||
template<typename Index>
|
||||
std::pair<final_node_type*,bool> final_transfer_(Index& x,final_node_type* n)
|
||||
{return final().transfer_(x,n);}
|
||||
|
||||
template<typename... Args>
|
||||
std::pair<final_node_type*,bool> final_emplace_(Args&&... args)
|
||||
template<BOOST_MULTI_INDEX_TEMPLATE_PARAM_PACK>
|
||||
std::pair<final_node_type*,bool> final_emplace_(
|
||||
BOOST_MULTI_INDEX_FUNCTION_PARAM_PACK)
|
||||
{
|
||||
return final().emplace_(std::forward<Args>(args)...);
|
||||
return final().emplace_(BOOST_MULTI_INDEX_FORWARD_PARAM_PACK);
|
||||
}
|
||||
|
||||
std::pair<final_node_type*,bool> final_insert_(
|
||||
@@ -261,41 +243,21 @@ protected:
|
||||
std::pair<final_node_type*,bool> final_insert_ref_(
|
||||
T& t,final_node_type* position)
|
||||
{return final().insert_ref_(t,position);}
|
||||
std::pair<final_node_type*,bool> final_insert_nh_(
|
||||
final_node_handle_type& nh,final_node_type* position)
|
||||
{return final().insert_nh_(nh,position);}
|
||||
|
||||
template<typename... Args>
|
||||
template<BOOST_MULTI_INDEX_TEMPLATE_PARAM_PACK>
|
||||
std::pair<final_node_type*,bool> final_emplace_hint_(
|
||||
final_node_type* position,Args&&... args)
|
||||
final_node_type* position,BOOST_MULTI_INDEX_FUNCTION_PARAM_PACK)
|
||||
{
|
||||
return final().emplace_hint_(position,std::forward<Args>(args)...);
|
||||
return final().emplace_hint_(
|
||||
position,BOOST_MULTI_INDEX_FORWARD_PARAM_PACK);
|
||||
}
|
||||
|
||||
final_node_handle_type final_extract_(final_node_type* x)
|
||||
{
|
||||
return final().extract_(x);
|
||||
}
|
||||
|
||||
template<typename Dst>
|
||||
void final_extract_for_transfer_(final_node_type* x,Dst dst)
|
||||
{
|
||||
final().extract_for_transfer_(x,dst);
|
||||
}
|
||||
|
||||
void final_erase_(final_node_type* x){final().erase_(x);}
|
||||
|
||||
void final_delete_node_(final_node_type* x){final().delete_node_(x);}
|
||||
void final_delete_all_nodes_(){final().delete_all_nodes_();}
|
||||
void final_clear_(){final().clear_();}
|
||||
|
||||
template<typename Index>
|
||||
void final_transfer_range_(
|
||||
Index& x,
|
||||
typename Index::iterator first,
|
||||
typename Index::iterator last)
|
||||
{final().transfer_range_(x,first,last);}
|
||||
|
||||
void final_swap_(final_type& x){final().swap_(x);}
|
||||
|
||||
bool final_replace_(
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2023 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2015 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,11 +15,11 @@
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <algorithm>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/archive/archive_exception.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
#include <boost/multi_index/detail/auto_space.hpp>
|
||||
#include <boost/multi_index/detail/bad_archive_exception.hpp>
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
#include <boost/serialization/nvp.hpp>
|
||||
#include <boost/throw_exception.hpp>
|
||||
#include <cstddef>
|
||||
|
||||
@@ -30,8 +30,7 @@ namespace multi_index{
|
||||
namespace detail{
|
||||
|
||||
/* Counterpart of index_saver (check index_saver.hpp for serialization
|
||||
* details.)
|
||||
* multi_index_container is in charge of supplying the info about
|
||||
* details.)* multi_index_container is in charge of supplying the info about
|
||||
* the base sequence, and each index can subsequently load itself using the
|
||||
* const interface of index_loader.
|
||||
*/
|
||||
@@ -48,14 +47,14 @@ public:
|
||||
template<class Archive>
|
||||
void add(Node* node,Archive& ar,const unsigned int)
|
||||
{
|
||||
ar>>core::make_nvp("position",*node);
|
||||
ar>>serialization::make_nvp("position",*node);
|
||||
entries()[n++]=node;
|
||||
}
|
||||
|
||||
template<class Archive>
|
||||
void add_track(Node* node,Archive& ar,const unsigned int)
|
||||
{
|
||||
ar>>core::make_nvp("position",*node);
|
||||
ar>>serialization::make_nvp("position",*node);
|
||||
}
|
||||
|
||||
/* A rearranger is passed two nodes, and is expected to
|
||||
@@ -103,7 +102,7 @@ private:
|
||||
FinalNode* unchecked_load_node(Archive& ar)const
|
||||
{
|
||||
Node* node=0;
|
||||
ar>>core::make_nvp("pointer",node);
|
||||
ar>>serialization::make_nvp("pointer",node);
|
||||
return static_cast<FinalNode*>(node);
|
||||
}
|
||||
|
||||
@@ -111,7 +110,7 @@ private:
|
||||
FinalNode* load_node(Archive& ar)const
|
||||
{
|
||||
Node* node=0;
|
||||
ar>>core::make_nvp("pointer",node);
|
||||
ar>>serialization::make_nvp("pointer",node);
|
||||
check_node(node);
|
||||
return static_cast<FinalNode*>(node);
|
||||
}
|
||||
@@ -119,7 +118,9 @@ private:
|
||||
void check_node(Node* node)const
|
||||
{
|
||||
if(node!=0&&!std::binary_search(entries(),entries()+size_,node)){
|
||||
throw_exception(bad_archive_exception());
|
||||
throw_exception(
|
||||
archive::archive_exception(
|
||||
archive::archive_exception::other_exception));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2022 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2015 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,7 +15,7 @@
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <algorithm>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
#include <boost/multi_index/detail/auto_space.hpp>
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
#include <cstddef>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2016 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -18,8 +18,8 @@
|
||||
#include <boost/type_traits/alignment_of.hpp>
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/multi_index/detail/bad_archive_exception.hpp>
|
||||
#include <boost/archive/archive_exception.hpp>
|
||||
#include <boost/serialization/access.hpp>
|
||||
#include <boost/throw_exception.hpp>
|
||||
#endif
|
||||
|
||||
@@ -105,19 +105,28 @@ Node* node_from_value(const Value* p)
|
||||
* somehow invalid archive.
|
||||
*/
|
||||
|
||||
#if defined(BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP)
|
||||
namespace serialization{
|
||||
#else
|
||||
namespace multi_index{
|
||||
namespace detail{
|
||||
#endif
|
||||
|
||||
template<class Archive,typename Value,typename Allocator>
|
||||
inline void load_construct_data(
|
||||
Archive&,boost::multi_index::detail::index_node_base<Value,Allocator>*,
|
||||
const unsigned int)
|
||||
{
|
||||
throw_exception(boost::multi_index::detail::bad_archive_exception());
|
||||
throw_exception(
|
||||
archive::archive_exception(archive::archive_exception::other_exception));
|
||||
}
|
||||
|
||||
#if defined(BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP)
|
||||
} /* namespace serialization */
|
||||
#else
|
||||
} /* namespace multi_index::detail */
|
||||
} /* namespace multi_index */
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2023 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,8 +15,8 @@
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/multi_index/detail/index_matcher.hpp>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
#include <boost/serialization/nvp.hpp>
|
||||
#include <cstddef>
|
||||
|
||||
namespace boost{
|
||||
@@ -43,14 +43,14 @@ public:
|
||||
template<class Archive>
|
||||
void add(Node* node,Archive& ar,const unsigned int)
|
||||
{
|
||||
ar<<core::make_nvp("position",*node);
|
||||
ar<<serialization::make_nvp("position",*node);
|
||||
alg.add(node);
|
||||
}
|
||||
|
||||
template<class Archive>
|
||||
void add_track(Node* node,Archive& ar,const unsigned int)
|
||||
{
|
||||
ar<<core::make_nvp("position",*node);
|
||||
ar<<serialization::make_nvp("position",*node);
|
||||
}
|
||||
|
||||
template<typename IndexIterator,class Archive>
|
||||
@@ -120,7 +120,7 @@ private:
|
||||
template<typename Archive>
|
||||
static void save_node(Node* node,Archive& ar)
|
||||
{
|
||||
ar<<core::make_nvp("pointer",node);
|
||||
ar<<serialization::make_nvp("pointer",node);
|
||||
}
|
||||
|
||||
index_matcher::algorithm<Node,Allocator> alg;
|
||||
|
||||
@@ -1,44 +0,0 @@
|
||||
/* Copyright 2003-2021 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_INVALIDATE_ITERATORS_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_INVALIDATE_ITERATORS_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* invalidate_iterators mimics the interface of index_access_sequence (see
|
||||
* index_access_sequence.hpp) but returns dummy indices whose iterator type
|
||||
* won't ever match those of the source: the net effect is that safe iterator
|
||||
* transfer resolves to iterator invalidation, so backbone function invocation
|
||||
* extract_(x,invalidate_iterators()) is used in extraction scenarios other
|
||||
* than merging.
|
||||
*/
|
||||
|
||||
struct invalidate_iterators
|
||||
{
|
||||
typedef void iterator;
|
||||
|
||||
invalidate_iterators& get(){return *this;}
|
||||
invalidate_iterators& next(){return *this;}
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2019 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -16,7 +16,8 @@
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/detail/workaround.hpp>
|
||||
|
||||
#if BOOST_WORKAROUND(_LIBCPP_VERSION,<30700)||\
|
||||
#if !defined(BOOST_NO_CXX11_HDR_TYPE_TRAITS)||\
|
||||
BOOST_WORKAROUND(_LIBCPP_VERSION,<30700)||\
|
||||
BOOST_WORKAROUND(BOOST_LIBSTDCXX_VERSION,<40802)
|
||||
/* libc++: std::is_function<void() const> fails,
|
||||
* https://bugs.llvm.org/show_bug.cgi?id=20084
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,18 +14,8 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
|
||||
#if defined(BOOST_MULTI_INDEX_ENABLE_MPL_SUPPORT)
|
||||
#include <boost/multi_index/detail/mpl_to_mp11_list.hpp>
|
||||
#define BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER \
|
||||
<boost/mpl/empty.hpp>
|
||||
#include BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#undef BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#define BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER \
|
||||
<boost/mpl/is_sequence.hpp>
|
||||
#include BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#undef BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#include <type_traits>
|
||||
#include <boost/mpl/empty.hpp>
|
||||
#include <boost/mpl/is_sequence.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -33,48 +23,18 @@ namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* an index list is a non-empty MPL sequence */
|
||||
|
||||
template<typename T>
|
||||
struct is_index_list
|
||||
{
|
||||
BOOST_STATIC_CONSTANT(bool,mpl_sequence=mpl::is_sequence<T>::value);
|
||||
BOOST_STATIC_CONSTANT(bool,non_empty=!(std::conditional<
|
||||
mpl_sequence,mpl::empty<T>,std::false_type>::type::value));
|
||||
BOOST_STATIC_CONSTANT(bool,non_empty=!mpl::empty<T>::value);
|
||||
BOOST_STATIC_CONSTANT(bool,value=mpl_sequence&&non_empty);
|
||||
};
|
||||
|
||||
template<typename IndexList>
|
||||
using mp11_index_list=mpl_to_mp11_list<IndexList>;
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
#else
|
||||
#include <type_traits>
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
template<typename T>
|
||||
struct is_index_list:std::false_type{};
|
||||
|
||||
/* an index list is a non-empty Mp11 list */
|
||||
template<template<typename...> class L,typename T,typename... Ts>
|
||||
struct is_index_list<L<T,Ts...>>:std::true_type{};
|
||||
|
||||
template<typename IndexList>
|
||||
using mp11_index_list=IndexList;
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2014 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,8 +14,8 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mpl/bool.hpp>
|
||||
#include <boost/type_traits/intrinsics.hpp>
|
||||
#include <type_traits>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -29,7 +29,7 @@ namespace detail{
|
||||
*/
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2,typename=void>
|
||||
struct is_transparent:std::true_type{};
|
||||
struct is_transparent:mpl::true_{};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
@@ -37,17 +37,21 @@ struct is_transparent:std::true_type{};
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#if !defined(BOOST_NO_SFINAE_EXPR)&& \
|
||||
#if !defined(BOOST_NO_SFINAE)&&!defined(BOOST_NO_SFINAE_EXPR)&& \
|
||||
!defined(BOOST_NO_CXX11_DECLTYPE)&& \
|
||||
(defined(BOOST_NO_CXX11_FINAL)||defined(BOOST_IS_FINAL))
|
||||
|
||||
#include <boost/core/enable_if.hpp>
|
||||
#include <boost/type_traits/declval.hpp>
|
||||
#include <boost/mpl/and.hpp>
|
||||
#include <boost/mpl/not.hpp>
|
||||
#include <boost/mpl/or.hpp>
|
||||
#include <boost/type_traits/function_traits.hpp>
|
||||
#include <boost/type_traits/is_class.hpp>
|
||||
#include <boost/type_traits/is_final.hpp>
|
||||
#include <boost/type_traits/is_function.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
#include <boost/type_traits/remove_pointer.hpp>
|
||||
#include <boost/utility/declval.hpp>
|
||||
#include <boost/utility/enable_if.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -66,7 +70,7 @@ struct is_transparent_class_helper:F
|
||||
};
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2,typename=void>
|
||||
struct is_transparent_class:std::true_type{};
|
||||
struct is_transparent_class:mpl::true_{};
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2>
|
||||
struct is_transparent_class<
|
||||
@@ -80,31 +84,38 @@ struct is_transparent_class<
|
||||
not_is_transparent_result_type
|
||||
>
|
||||
>::type
|
||||
>:std::false_type{};
|
||||
>:mpl::false_{};
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2>
|
||||
struct is_transparent<
|
||||
F,Arg1,Arg2,
|
||||
typename enable_if_c<
|
||||
is_class<F>::value&&
|
||||
!is_final<F>::value /* is_transparent_class_helper derives from F */
|
||||
typename enable_if<
|
||||
mpl::and_<
|
||||
is_class<F>,
|
||||
mpl::not_<is_final<F> > /* is_transparent_class_helper derives from F */
|
||||
>
|
||||
>::type
|
||||
>:is_transparent_class<F,Arg1,Arg2>{};
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2,typename=void>
|
||||
struct is_transparent_function:std::true_type{};
|
||||
struct is_transparent_function:mpl::true_{};
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2>
|
||||
struct is_transparent_function<
|
||||
F,Arg1,Arg2,
|
||||
typename enable_if_c<
|
||||
!(is_same<typename function_traits<F>::arg1_type,const Arg1&>::value||
|
||||
is_same<typename function_traits<F>::arg1_type,Arg1>::value)
|
||||
||
|
||||
!(is_same<typename function_traits<F>::arg2_type,const Arg2&>::value||
|
||||
is_same<typename function_traits<F>::arg2_type,Arg2>::value)
|
||||
typename enable_if<
|
||||
mpl::or_<
|
||||
mpl::not_<mpl::or_<
|
||||
is_same<typename function_traits<F>::arg1_type,const Arg1&>,
|
||||
is_same<typename function_traits<F>::arg1_type,Arg1>
|
||||
> >,
|
||||
mpl::not_<mpl::or_<
|
||||
is_same<typename function_traits<F>::arg2_type,const Arg2&>,
|
||||
is_same<typename function_traits<F>::arg2_type,Arg2>
|
||||
> >
|
||||
>
|
||||
>::type
|
||||
>:std::false_type{};
|
||||
>:mpl::false_{};
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2>
|
||||
struct is_transparent<
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,7 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/utility.hpp>
|
||||
#include <boost/mpl/apply.hpp>
|
||||
#include <boost/operators.hpp>
|
||||
|
||||
namespace boost{
|
||||
@@ -125,7 +125,10 @@ template<>
|
||||
struct iter_adaptor_selector<std::forward_iterator_tag>
|
||||
{
|
||||
template<class Derived,class Base>
|
||||
using fn=forward_iter_adaptor_base<Derived,Base>;
|
||||
struct apply
|
||||
{
|
||||
typedef forward_iter_adaptor_base<Derived,Base> type;
|
||||
};
|
||||
};
|
||||
|
||||
template<class Derived,class Base>
|
||||
@@ -180,7 +183,10 @@ template<>
|
||||
struct iter_adaptor_selector<std::bidirectional_iterator_tag>
|
||||
{
|
||||
template<class Derived,class Base>
|
||||
using fn=bidirectional_iter_adaptor_base<Derived,Base>;
|
||||
struct apply
|
||||
{
|
||||
typedef bidirectional_iter_adaptor_base<Derived,Base> type;
|
||||
};
|
||||
};
|
||||
|
||||
template<class Derived,class Base>
|
||||
@@ -277,17 +283,23 @@ template<>
|
||||
struct iter_adaptor_selector<std::random_access_iterator_tag>
|
||||
{
|
||||
template<class Derived,class Base>
|
||||
using fn=random_access_iter_adaptor_base<Derived,Base>;
|
||||
struct apply
|
||||
{
|
||||
typedef random_access_iter_adaptor_base<Derived,Base> type;
|
||||
};
|
||||
};
|
||||
|
||||
template<class Derived,class Base>
|
||||
using iter_adaptor_base=mp11::mp_invoke_q<
|
||||
iter_adaptor_selector<typename Base::iterator_category>,
|
||||
Derived,Base
|
||||
>;
|
||||
struct iter_adaptor_base
|
||||
{
|
||||
typedef iter_adaptor_selector<
|
||||
typename Base::iterator_category> selector;
|
||||
typedef typename mpl::apply2<
|
||||
selector,Derived,Base>::type type;
|
||||
};
|
||||
|
||||
template<class Derived,class Base>
|
||||
class iter_adaptor:public iter_adaptor_base<Derived,Base>
|
||||
class iter_adaptor:public iter_adaptor_base<Derived,Base>::type
|
||||
{
|
||||
protected:
|
||||
iter_adaptor(){}
|
||||
|
||||
@@ -1,62 +0,0 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_MPL_TO_MP11_LIST_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_MPL_TO_MP11_LIST_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#if defined(BOOST_MULTI_INDEX_ENABLE_MPL_SUPPORT)
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/list.hpp>
|
||||
#define BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER \
|
||||
<boost/mpl/begin_end.hpp>
|
||||
#include BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#undef BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#define BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER \
|
||||
<boost/mpl/deref.hpp>
|
||||
#include BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#undef BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#define BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER \
|
||||
<boost/mpl/next.hpp>
|
||||
#include BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#undef BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
template<typename First,typename Last,typename... Ts>
|
||||
struct mpl_to_mp11_list_impl:mpl_to_mp11_list_impl<
|
||||
typename mpl::next<First>::type,Last,
|
||||
Ts...,typename mpl::deref<First>::type
|
||||
>{};
|
||||
|
||||
template<typename Last,typename... Ts>
|
||||
struct mpl_to_mp11_list_impl<Last,Last,Ts...>
|
||||
{
|
||||
using type=mp11::mp_list<Ts...>;
|
||||
};
|
||||
|
||||
template<typename TypeList>
|
||||
using mpl_to_mp11_list=typename mpl_to_mp11_list_impl<
|
||||
typename mpl::begin<TypeList>::type,
|
||||
typename boost::mpl::end<TypeList>::type
|
||||
>::type;
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
#endif
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,8 +14,8 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/algorithm.hpp>
|
||||
#include <type_traits>
|
||||
#include <boost/mpl/fold.hpp>
|
||||
#include <boost/mpl/set/set0.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -25,11 +25,68 @@ namespace detail{
|
||||
|
||||
/* no_duplicate_tags check at compile-time that a tag list
|
||||
* has no duplicate tags.
|
||||
* The algorithm deserves some explanation: tags
|
||||
* are sequentially inserted into a mpl::set if they were
|
||||
* not already present. Due to the magic of mpl::set
|
||||
* (mpl::has_key is contant time), this operation takes linear
|
||||
* time, and even MSVC++ 6.5 handles it gracefully (other obvious
|
||||
* solutions are quadratic.)
|
||||
*/
|
||||
|
||||
struct duplicate_tag_mark{};
|
||||
|
||||
struct duplicate_tag_marker
|
||||
{
|
||||
template <typename MplSet,typename Tag>
|
||||
struct apply
|
||||
{
|
||||
typedef mpl::s_item<
|
||||
typename mpl::if_<mpl::has_key<MplSet,Tag>,duplicate_tag_mark,Tag>::type,
|
||||
MplSet
|
||||
> type;
|
||||
};
|
||||
};
|
||||
|
||||
template<typename TagList>
|
||||
using no_duplicate_tags=
|
||||
std::is_same<TagList,mp11::mp_unique<TagList>>;
|
||||
struct no_duplicate_tags
|
||||
{
|
||||
typedef typename mpl::fold<
|
||||
TagList,
|
||||
mpl::set0<>,
|
||||
duplicate_tag_marker
|
||||
>::type aux;
|
||||
|
||||
BOOST_STATIC_CONSTANT(
|
||||
bool,value=!(mpl::has_key<aux,duplicate_tag_mark>::value));
|
||||
};
|
||||
|
||||
/* Variant for an index list: duplication is checked
|
||||
* across all the indices.
|
||||
*/
|
||||
|
||||
struct duplicate_tag_list_marker
|
||||
{
|
||||
template <typename MplSet,typename Index>
|
||||
struct apply:mpl::fold<
|
||||
BOOST_DEDUCED_TYPENAME Index::tag_list,
|
||||
MplSet,
|
||||
duplicate_tag_marker>
|
||||
{
|
||||
};
|
||||
};
|
||||
|
||||
template<typename IndexList>
|
||||
struct no_duplicate_tags_in_index_list
|
||||
{
|
||||
typedef typename mpl::fold<
|
||||
IndexList,
|
||||
mpl::set0<>,
|
||||
duplicate_tag_list_marker
|
||||
>::type aux;
|
||||
|
||||
BOOST_STATIC_CONSTANT(
|
||||
bool,value=!(mpl::has_key<aux,duplicate_tag_mark>::value));
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
|
||||
@@ -1,44 +0,0 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_NO_DUPLICATE_TAGS_IN_INDEX_LIST_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_NO_DUPLICATE_TAGS_IN_INDEX_LIST_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/multi_index/tag.hpp>
|
||||
#include <boost/mp11/algorithm.hpp>
|
||||
#include <boost/mp11/list.hpp>
|
||||
#include <type_traits>
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* checks duplication of tags across all indices of a container */
|
||||
|
||||
template<typename Index>
|
||||
using index_tag_list=mp11::mp_rename<
|
||||
mp11_tag_list<typename Index::tag_list>,mp11::mp_list>;
|
||||
|
||||
template<typename IndexList>
|
||||
using no_duplicate_tags_in_index_list=no_duplicate_tags<
|
||||
mp11::mp_flatten<mp11::mp_transform<index_tag_list,IndexList>>>;
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,244 +0,0 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_NODE_HANDLE_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_NODE_HANDLE_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <algorithm>
|
||||
#include <boost/core/addressof.hpp>
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <boost/core/enable_if.hpp>
|
||||
#include <boost/detail/workaround.hpp>
|
||||
#include <boost/multi_index_container_fwd.hpp>
|
||||
#include <boost/type_traits/aligned_storage.hpp>
|
||||
#include <boost/type_traits/alignment_of.hpp>
|
||||
#include <boost/type_traits/is_const.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
#include <new>
|
||||
#include <utility>
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* Node handle template class following [container.node] specs.
|
||||
*/
|
||||
|
||||
#include <boost/multi_index/detail/define_if_constexpr_macro.hpp>
|
||||
|
||||
template<typename Node,typename Allocator>
|
||||
class node_handle
|
||||
{
|
||||
public:
|
||||
typedef typename Node::value_type value_type;
|
||||
typedef Allocator allocator_type;
|
||||
|
||||
node_handle()BOOST_NOEXCEPT:node(0){}
|
||||
|
||||
node_handle(node_handle&& x)BOOST_NOEXCEPT:node(x.node)
|
||||
{
|
||||
if(!x.empty()){
|
||||
move_construct_allocator(std::move(x));
|
||||
x.destroy_allocator();
|
||||
x.node=0;
|
||||
}
|
||||
}
|
||||
|
||||
~node_handle()
|
||||
{
|
||||
if(!empty()){
|
||||
delete_node();
|
||||
destroy_allocator();
|
||||
}
|
||||
}
|
||||
|
||||
node_handle& operator=(node_handle&& x)
|
||||
{
|
||||
if(this!=&x){
|
||||
if(!empty()){
|
||||
delete_node();
|
||||
if(!x.empty()){
|
||||
BOOST_MULTI_INDEX_IF_CONSTEXPR(
|
||||
allocator_propagate_on_container_move_assignment_t<
|
||||
allocator_type>::value){
|
||||
move_assign_allocator(std::move(x));
|
||||
}
|
||||
x.destroy_allocator();
|
||||
}
|
||||
else{
|
||||
destroy_allocator();
|
||||
}
|
||||
}
|
||||
else if(!x.empty()){
|
||||
move_construct_allocator(std::move(x));
|
||||
x.destroy_allocator();
|
||||
}
|
||||
node=x.node;
|
||||
x.node=0;
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
value_type& value()const{return node->value();}
|
||||
allocator_type get_allocator()const{return *allocator_ptr();}
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_EXPLICIT_CONVERSION_OPERATORS)
|
||||
explicit
|
||||
#endif
|
||||
operator bool()const BOOST_NOEXCEPT{return (node!=0);}
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_GCC_VERSION,>=70000)&&__cplusplus<201103L
|
||||
/* https://github.com/boostorg/config/issues/336 */
|
||||
#else
|
||||
BOOST_ATTRIBUTE_NODISCARD
|
||||
#endif
|
||||
bool empty()const BOOST_NOEXCEPT{return (node==0);}
|
||||
|
||||
void swap(node_handle& x)
|
||||
BOOST_NOEXCEPT_IF(
|
||||
allocator_propagate_on_container_swap_t<allocator_type>::value||
|
||||
allocator_is_always_equal_t<allocator_type>::value)
|
||||
{
|
||||
if(!empty()){
|
||||
if(!x.empty()){
|
||||
BOOST_MULTI_INDEX_IF_CONSTEXPR(
|
||||
allocator_propagate_on_container_swap_t<allocator_type>::value){
|
||||
using std::swap;
|
||||
swap(*allocator_ptr(),*x.allocator_ptr());
|
||||
}
|
||||
}
|
||||
else{
|
||||
x.move_construct_allocator(std::move(*this));
|
||||
destroy_allocator();
|
||||
}
|
||||
}
|
||||
else if(!x.empty()){
|
||||
move_construct_allocator(std::move(x));
|
||||
x.destroy_allocator();
|
||||
}
|
||||
std::swap(node,x.node);
|
||||
}
|
||||
|
||||
friend void swap(node_handle& x,node_handle& y)
|
||||
BOOST_NOEXCEPT_IF(noexcept(x.swap(y)))
|
||||
{
|
||||
x.swap(y);
|
||||
}
|
||||
|
||||
private:
|
||||
template <typename,typename,typename>
|
||||
friend class boost::multi_index::multi_index_container;
|
||||
|
||||
node_handle(Node* node_,const allocator_type& al):node(node_)
|
||||
{
|
||||
::new (static_cast<void*>(allocator_ptr())) allocator_type(al);
|
||||
}
|
||||
|
||||
void release_node()
|
||||
{
|
||||
if(!empty()){
|
||||
node=0;
|
||||
destroy_allocator();
|
||||
}
|
||||
}
|
||||
|
||||
#include <boost/multi_index/detail/ignore_wstrict_aliasing.hpp>
|
||||
|
||||
const allocator_type* allocator_ptr()const
|
||||
{
|
||||
return reinterpret_cast<const allocator_type*>(&space);
|
||||
}
|
||||
|
||||
allocator_type* allocator_ptr()
|
||||
{
|
||||
return reinterpret_cast<allocator_type*>(&space);
|
||||
}
|
||||
|
||||
#include <boost/multi_index/detail/restore_wstrict_aliasing.hpp>
|
||||
|
||||
void move_construct_allocator(node_handle&& x)
|
||||
{
|
||||
::new (static_cast<void*>(allocator_ptr()))
|
||||
allocator_type(std::move(*x.allocator_ptr()));
|
||||
}
|
||||
|
||||
void move_assign_allocator(node_handle&& x)
|
||||
{
|
||||
*allocator_ptr()=std::move(*x.allocator_ptr());
|
||||
}
|
||||
|
||||
void destroy_allocator(){allocator_ptr()->~allocator_type();}
|
||||
|
||||
void delete_node()
|
||||
{
|
||||
typedef allocator_rebind_t<allocator_type,Node> node_allocator;
|
||||
typedef allocator_pointer_t<node_allocator> node_pointer;
|
||||
|
||||
allocator_destroy(*allocator_ptr(),boost::addressof(node->value()));
|
||||
node_allocator nal(*allocator_ptr());
|
||||
allocator_deallocate(nal,static_cast<node_pointer>(node),1);
|
||||
}
|
||||
|
||||
Node* node;
|
||||
typename aligned_storage<
|
||||
sizeof(allocator_type),
|
||||
alignment_of<allocator_type>::value
|
||||
>::type space;
|
||||
};
|
||||
|
||||
#include <boost/multi_index/detail/undef_if_constexpr_macro.hpp>
|
||||
|
||||
/* node handle insert return type template class following
|
||||
* [container.insert.return] specs.
|
||||
*/
|
||||
|
||||
template<typename Iterator,typename NodeHandle>
|
||||
struct insert_return_type
|
||||
{
|
||||
insert_return_type(
|
||||
Iterator position_,bool inserted_,NodeHandle&& node_):
|
||||
position(position_),inserted(inserted_),node(std::move(node_)){}
|
||||
insert_return_type(insert_return_type&& x):
|
||||
position(x.position),inserted(x.inserted),node(std::move(x.node)){}
|
||||
|
||||
insert_return_type& operator=(insert_return_type&& x)
|
||||
{
|
||||
position=x.position;
|
||||
inserted=x.inserted;
|
||||
node=std::move(x.node);
|
||||
return *this;
|
||||
}
|
||||
|
||||
Iterator position;
|
||||
bool inserted;
|
||||
NodeHandle node;
|
||||
};
|
||||
|
||||
/* utility for SFINAEing merge and related operations */
|
||||
|
||||
#define BOOST_MULTI_INDEX_ENABLE_IF_MERGEABLE(Dst,Src,T) \
|
||||
typename enable_if_c< \
|
||||
!is_const< Dst >::value&&!is_const< Src >::value&& \
|
||||
is_same<typename Dst::node_type,typename Src::node_type>::value, \
|
||||
T \
|
||||
>::type
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,10 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/algorithm.hpp>
|
||||
#include <boost/detail/workaround.hpp>
|
||||
#include <boost/mpl/bind.hpp>
|
||||
#include <boost/mpl/reverse_iter_fold.hpp>
|
||||
#include <boost/mpl/deref.hpp>
|
||||
#include <boost/multi_index_container_fwd.hpp>
|
||||
#include <boost/multi_index/detail/header_holder.hpp>
|
||||
#include <boost/multi_index/detail/index_node_base.hpp>
|
||||
@@ -27,23 +30,31 @@ namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* Mp11 machinery to construct the internal node type associated to an
|
||||
/* MPL machinery to construct the internal node type associated to an
|
||||
* index list.
|
||||
*/
|
||||
|
||||
template<typename IndexSpecifier,typename Super>
|
||||
using node_type=typename IndexSpecifier::template node_class<Super>::type;
|
||||
struct index_node_applier
|
||||
{
|
||||
template<typename IndexSpecifierIterator,typename Super>
|
||||
struct apply
|
||||
{
|
||||
typedef typename mpl::deref<IndexSpecifierIterator>::type index_specifier;
|
||||
typedef typename index_specifier::
|
||||
BOOST_NESTED_TEMPLATE node_class<Super>::type type;
|
||||
};
|
||||
};
|
||||
|
||||
template<typename Value,typename IndexSpecifierList,typename Allocator>
|
||||
struct multi_index_node_type
|
||||
{
|
||||
BOOST_STATIC_ASSERT(detail::is_index_list<IndexSpecifierList>::value);
|
||||
|
||||
typedef mp11::mp_reverse_fold<
|
||||
detail::mp11_index_list<IndexSpecifierList>,
|
||||
typedef typename mpl::reverse_iter_fold<
|
||||
IndexSpecifierList,
|
||||
index_node_base<Value,Allocator>,
|
||||
node_type
|
||||
> type;
|
||||
mpl::bind2<index_node_applier,mpl::_2,mpl::_1>
|
||||
>::type type;
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,11 +14,14 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/utility.hpp>
|
||||
#include <boost/mpl/aux_/na.hpp>
|
||||
#include <boost/mpl/eval_if.hpp>
|
||||
#include <boost/mpl/identity.hpp>
|
||||
#include <boost/mpl/if.hpp>
|
||||
#include <boost/multi_index/tag.hpp>
|
||||
#include <boost/static_assert.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
#include <functional>
|
||||
#include <type_traits>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -37,33 +40,38 @@ namespace detail{
|
||||
* polymorphism.
|
||||
*/
|
||||
|
||||
template<typename KeyFromValue>
|
||||
struct index_args_default_compare
|
||||
{
|
||||
typedef std::less<typename KeyFromValue::result_type> type;
|
||||
};
|
||||
|
||||
template<typename Arg1,typename Arg2,typename Arg3>
|
||||
struct ordered_index_args
|
||||
{
|
||||
typedef is_tag<Arg1> full_form;
|
||||
|
||||
typedef mp11::mp_if<
|
||||
typedef typename mpl::if_<
|
||||
full_form,
|
||||
Arg1,
|
||||
tag< > > tag_list_type;
|
||||
typedef mp11::mp_if<
|
||||
tag< > >::type tag_list_type;
|
||||
typedef typename mpl::if_<
|
||||
full_form,
|
||||
Arg2,
|
||||
Arg1> key_from_value_type;
|
||||
typedef mp11::mp_if<
|
||||
Arg1>::type key_from_value_type;
|
||||
typedef typename mpl::if_<
|
||||
full_form,
|
||||
Arg3,
|
||||
Arg2> supplied_compare_type;
|
||||
typedef mp11::mp_eval_if_c<
|
||||
!std::is_void<supplied_compare_type>::value,
|
||||
supplied_compare_type,
|
||||
std::less,
|
||||
typename key_from_value_type::result_type
|
||||
> compare_type;
|
||||
Arg2>::type supplied_compare_type;
|
||||
typedef typename mpl::eval_if<
|
||||
mpl::is_na<supplied_compare_type>,
|
||||
index_args_default_compare<key_from_value_type>,
|
||||
mpl::identity<supplied_compare_type>
|
||||
>::type compare_type;
|
||||
|
||||
BOOST_STATIC_ASSERT(is_tag<tag_list_type>::value);
|
||||
BOOST_STATIC_ASSERT(!std::is_void<key_from_value_type>::value);
|
||||
BOOST_STATIC_ASSERT(!std::is_void<compare_type>::value);
|
||||
BOOST_STATIC_ASSERT(!mpl::is_na<key_from_value_type>::value);
|
||||
BOOST_STATIC_ASSERT(!mpl::is_na<compare_type>::value);
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
@@ -72,4 +80,4 @@ struct ordered_index_args
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
#endif
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2019 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -41,12 +41,13 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <cstddef>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_COMPRESSED_ORDERED_INDEX_NODES)
|
||||
#include <boost/mp11/utility.hpp>
|
||||
#include <boost/mpl/and.hpp>
|
||||
#include <boost/mpl/if.hpp>
|
||||
#include <boost/multi_index/detail/uintptr_type.hpp>
|
||||
#include <boost/type_traits/alignment_of.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
@@ -69,14 +70,15 @@ struct ordered_index_node_impl; /* fwd decl. */
|
||||
template<typename AugmentPolicy,typename Allocator>
|
||||
struct ordered_index_node_traits
|
||||
{
|
||||
typedef allocator_rebind_t<
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,
|
||||
ordered_index_node_impl<AugmentPolicy,Allocator>
|
||||
> allocator;
|
||||
typedef allocator_pointer_t<allocator> pointer;
|
||||
typedef allocator_const_pointer_t<allocator> const_pointer;
|
||||
typedef allocator_difference_type_t<allocator> difference_type;
|
||||
typedef allocator_size_type_t<allocator> size_type;
|
||||
>::type allocator;
|
||||
typedef allocator_traits<allocator> alloc_traits;
|
||||
typedef typename alloc_traits::pointer pointer;
|
||||
typedef typename alloc_traits::const_pointer const_pointer;
|
||||
typedef typename alloc_traits::difference_type difference_type;
|
||||
typedef typename alloc_traits::size_type size_type;
|
||||
};
|
||||
|
||||
template<typename AugmentPolicy,typename Allocator>
|
||||
@@ -131,7 +133,6 @@ struct ordered_index_node_compressed_base
|
||||
{
|
||||
typedef ordered_index_node_traits<
|
||||
AugmentPolicy,Allocator> node_traits;
|
||||
typedef typename node_traits::allocator node_allocator;
|
||||
typedef ordered_index_node_impl<
|
||||
AugmentPolicy,Allocator>* pointer;
|
||||
typedef const ordered_index_node_impl<
|
||||
@@ -227,7 +228,7 @@ struct ordered_index_node_impl_base:
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_COMPRESSED_ORDERED_INDEX_NODES)
|
||||
AugmentPolicy::template augmented_node<
|
||||
mp11::mp_if_c<
|
||||
typename mpl::if_c<
|
||||
!(has_uintptr_type::value)||
|
||||
(alignment_of<
|
||||
ordered_index_node_compressed_base<AugmentPolicy,Allocator>
|
||||
@@ -237,7 +238,7 @@ struct ordered_index_node_impl_base:
|
||||
ordered_index_node_impl<AugmentPolicy,Allocator>*>::value),
|
||||
ordered_index_node_std_base<AugmentPolicy,Allocator>,
|
||||
ordered_index_node_compressed_base<AugmentPolicy,Allocator>
|
||||
>
|
||||
>::type
|
||||
>::type
|
||||
#else
|
||||
AugmentPolicy::template augmented_node<
|
||||
@@ -411,7 +412,7 @@ public:
|
||||
ordered_index_node_impl::rebalance(x,header->parent());
|
||||
}
|
||||
|
||||
static pointer rebalance_for_extract(
|
||||
static pointer rebalance_for_erase(
|
||||
pointer z,parent_ref root,pointer& leftmost,pointer& rightmost)
|
||||
{
|
||||
pointer y=z;
|
||||
@@ -579,18 +580,18 @@ template<typename AugmentPolicy,typename Super>
|
||||
struct ordered_index_node_trampoline:
|
||||
ordered_index_node_impl<
|
||||
AugmentPolicy,
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
typename Super::allocator_type,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
>
|
||||
{
|
||||
typedef ordered_index_node_impl<
|
||||
AugmentPolicy,
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
typename Super::allocator_type,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
> impl_type;
|
||||
};
|
||||
|
||||
@@ -609,14 +610,6 @@ public:
|
||||
typedef typename trampoline::const_pointer const_impl_pointer;
|
||||
typedef typename trampoline::difference_type difference_type;
|
||||
typedef typename trampoline::size_type size_type;
|
||||
typedef allocator_rebind_t<
|
||||
typename trampoline::node_allocator,
|
||||
ordered_index_node> final_allocator_type;
|
||||
typedef allocator_pointer_t<
|
||||
final_allocator_type> pointer;
|
||||
typedef allocator_const_pointer_t<
|
||||
final_allocator_type> const_pointer;
|
||||
|
||||
|
||||
impl_color_ref color(){return trampoline::color();}
|
||||
ordered_index_color color()const{return trampoline::color();}
|
||||
@@ -655,24 +648,20 @@ public:
|
||||
raw_ptr<const impl_type*>(x)));
|
||||
}
|
||||
|
||||
/* Interoperability with bidir_node_iterator and index impl.
|
||||
* Templated for raw-pointer/non-raw-pointer versions.
|
||||
*/
|
||||
/* interoperability with bidir_node_iterator */
|
||||
|
||||
template<typename NodePtr>
|
||||
static void increment(NodePtr& x)
|
||||
static void increment(ordered_index_node*& x)
|
||||
{
|
||||
impl_pointer xi=x->impl();
|
||||
trampoline::increment(xi);
|
||||
x=NodePtr(from_impl(xi));
|
||||
x=from_impl(xi);
|
||||
}
|
||||
|
||||
template<typename NodePtr>
|
||||
static void decrement(NodePtr& x)
|
||||
static void decrement(ordered_index_node*& x)
|
||||
{
|
||||
impl_pointer xi=x->impl();
|
||||
trampoline::decrement(xi);
|
||||
x=NodePtr(from_impl(xi));
|
||||
x=from_impl(xi);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2014 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -41,9 +41,8 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/function.hpp>
|
||||
#include <boost/mpl/and.hpp>
|
||||
#include <boost/multi_index/detail/promotes_arg.hpp>
|
||||
#include <type_traits>
|
||||
#include <utility>
|
||||
|
||||
namespace boost{
|
||||
@@ -71,7 +70,7 @@ inline Node* ordered_index_find(
|
||||
|
||||
return ordered_index_find(
|
||||
top,y,key,x,comp,
|
||||
mp11::mp_and<
|
||||
mpl::and_<
|
||||
promotes_1st_arg<CompatibleCompare,CompatibleKey,key_type>,
|
||||
promotes_2nd_arg<CompatibleCompare,key_type,CompatibleKey> >());
|
||||
}
|
||||
@@ -82,10 +81,10 @@ template<
|
||||
>
|
||||
inline Node* ordered_index_find(
|
||||
Node* top,Node* y,const KeyFromValue& key,
|
||||
const typename KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,std::true_type)
|
||||
const BOOST_DEDUCED_TYPENAME KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,mpl::true_)
|
||||
{
|
||||
return ordered_index_find(top,y,key,x,comp,std::false_type());
|
||||
return ordered_index_find(top,y,key,x,comp,mpl::false_());
|
||||
}
|
||||
|
||||
template<
|
||||
@@ -94,7 +93,7 @@ template<
|
||||
>
|
||||
inline Node* ordered_index_find(
|
||||
Node* top,Node* y,const KeyFromValue& key,const CompatibleKey& x,
|
||||
const CompatibleCompare& comp,std::false_type)
|
||||
const CompatibleCompare& comp,mpl::false_)
|
||||
{
|
||||
Node* y0=y;
|
||||
|
||||
@@ -130,10 +129,10 @@ template<
|
||||
>
|
||||
inline Node* ordered_index_lower_bound(
|
||||
Node* top,Node* y,const KeyFromValue& key,
|
||||
const typename KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,std::true_type)
|
||||
const BOOST_DEDUCED_TYPENAME KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,mpl::true_)
|
||||
{
|
||||
return ordered_index_lower_bound(top,y,key,x,comp,std::false_type());
|
||||
return ordered_index_lower_bound(top,y,key,x,comp,mpl::false_());
|
||||
}
|
||||
|
||||
template<
|
||||
@@ -142,7 +141,7 @@ template<
|
||||
>
|
||||
inline Node* ordered_index_lower_bound(
|
||||
Node* top,Node* y,const KeyFromValue& key,const CompatibleKey& x,
|
||||
const CompatibleCompare& comp,std::false_type)
|
||||
const CompatibleCompare& comp,mpl::false_)
|
||||
{
|
||||
while(top){
|
||||
if(!comp(key(top->value()),x)){
|
||||
@@ -176,10 +175,10 @@ template<
|
||||
>
|
||||
inline Node* ordered_index_upper_bound(
|
||||
Node* top,Node* y,const KeyFromValue& key,
|
||||
const typename KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,std::true_type)
|
||||
const BOOST_DEDUCED_TYPENAME KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,mpl::true_)
|
||||
{
|
||||
return ordered_index_upper_bound(top,y,key,x,comp,std::false_type());
|
||||
return ordered_index_upper_bound(top,y,key,x,comp,mpl::false_());
|
||||
}
|
||||
|
||||
template<
|
||||
@@ -188,7 +187,7 @@ template<
|
||||
>
|
||||
inline Node* ordered_index_upper_bound(
|
||||
Node* top,Node* y,const KeyFromValue& key,const CompatibleKey& x,
|
||||
const CompatibleCompare& comp,std::false_type)
|
||||
const CompatibleCompare& comp,mpl::false_)
|
||||
{
|
||||
while(top){
|
||||
if(comp(x,key(top->value()))){
|
||||
@@ -213,7 +212,7 @@ inline std::pair<Node*,Node*> ordered_index_equal_range(
|
||||
|
||||
return ordered_index_equal_range(
|
||||
top,y,key,x,comp,
|
||||
mp11::mp_and<
|
||||
mpl::and_<
|
||||
promotes_1st_arg<CompatibleCompare,CompatibleKey,key_type>,
|
||||
promotes_2nd_arg<CompatibleCompare,key_type,CompatibleKey> >());
|
||||
}
|
||||
@@ -224,10 +223,10 @@ template<
|
||||
>
|
||||
inline std::pair<Node*,Node*> ordered_index_equal_range(
|
||||
Node* top,Node* y,const KeyFromValue& key,
|
||||
const typename KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,std::true_type)
|
||||
const BOOST_DEDUCED_TYPENAME KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,mpl::true_)
|
||||
{
|
||||
return ordered_index_equal_range(top,y,key,x,comp,std::false_type());
|
||||
return ordered_index_equal_range(top,y,key,x,comp,mpl::false_());
|
||||
}
|
||||
|
||||
template<
|
||||
@@ -236,7 +235,7 @@ template<
|
||||
>
|
||||
inline std::pair<Node*,Node*> ordered_index_equal_range(
|
||||
Node* top,Node* y,const KeyFromValue& key,const CompatibleKey& x,
|
||||
const CompatibleCompare& comp,std::false_type)
|
||||
const CompatibleCompare& comp,mpl::false_)
|
||||
{
|
||||
while(top){
|
||||
if(comp(key(top->value()),x)){
|
||||
@@ -249,9 +248,9 @@ inline std::pair<Node*,Node*> ordered_index_equal_range(
|
||||
else{
|
||||
return std::pair<Node*,Node*>(
|
||||
ordered_index_lower_bound(
|
||||
Node::from_impl(top->left()),top,key,x,comp,std::false_type()),
|
||||
Node::from_impl(top->left()),top,key,x,comp,mpl::false_()),
|
||||
ordered_index_upper_bound(
|
||||
Node::from_impl(top->right()),y,key,x,comp,std::false_type()));
|
||||
Node::from_impl(top->right()),y,key,x,comp,mpl::false_()));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2017 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,7 +15,6 @@
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/detail/workaround.hpp>
|
||||
#include <type_traits>
|
||||
|
||||
/* Metafunctions to check if f(arg1,arg2) promotes either arg1 to the type of
|
||||
* arg2 or viceversa. By default, (i.e. if it cannot be determined), no
|
||||
@@ -31,10 +30,10 @@ namespace multi_index{
|
||||
namespace detail{
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2>
|
||||
struct promotes_1st_arg:std::false_type{};
|
||||
struct promotes_1st_arg:mpl::false_{};
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2>
|
||||
struct promotes_2nd_arg:std::false_type{};
|
||||
struct promotes_2nd_arg:mpl::false_{};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
@@ -44,7 +43,9 @@ struct promotes_2nd_arg:std::false_type{};
|
||||
|
||||
#else
|
||||
|
||||
#include <boost/mp11/function.hpp>
|
||||
#include <boost/mpl/and.hpp>
|
||||
#include <boost/mpl/bool.hpp>
|
||||
#include <boost/mpl/not.hpp>
|
||||
#include <boost/multi_index/detail/is_transparent.hpp>
|
||||
#include <boost/type_traits/is_convertible.hpp>
|
||||
|
||||
@@ -56,8 +57,8 @@ namespace detail{
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2>
|
||||
struct promotes_1st_arg:
|
||||
mp11::mp_and<
|
||||
mp11::mp_not<is_transparent<F,Arg1,Arg2> >,
|
||||
mpl::and_<
|
||||
mpl::not_<is_transparent<F,Arg1,Arg2> >,
|
||||
is_convertible<const Arg1,Arg2>,
|
||||
is_transparent<F,Arg2,Arg2>
|
||||
>
|
||||
@@ -65,8 +66,8 @@ struct promotes_1st_arg:
|
||||
|
||||
template<typename F,typename Arg1,typename Arg2>
|
||||
struct promotes_2nd_arg:
|
||||
mp11::mp_and<
|
||||
mp11::mp_not<is_transparent<F,Arg1,Arg2> >,
|
||||
mpl::and_<
|
||||
mpl::not_<is_transparent<F,Arg1,Arg2> >,
|
||||
is_convertible<const Arg2,Arg1>,
|
||||
is_transparent<F,Arg1,Arg1>
|
||||
>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2015 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,8 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <type_traits>
|
||||
#include <boost/mpl/bool.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -25,13 +26,13 @@ namespace detail{
|
||||
/* gets the underlying pointer of a pointer-like value */
|
||||
|
||||
template<typename RawPointer>
|
||||
inline RawPointer raw_ptr(RawPointer const& p,std::true_type)
|
||||
inline RawPointer raw_ptr(RawPointer const& p,mpl::true_)
|
||||
{
|
||||
return p;
|
||||
}
|
||||
|
||||
template<typename RawPointer,typename Pointer>
|
||||
inline RawPointer raw_ptr(Pointer const& p,std::false_type)
|
||||
inline RawPointer raw_ptr(Pointer const& p,mpl::false_)
|
||||
{
|
||||
return p==Pointer(0)?0:&*p;
|
||||
}
|
||||
@@ -39,7 +40,7 @@ inline RawPointer raw_ptr(Pointer const& p,std::false_type)
|
||||
template<typename RawPointer,typename Pointer>
|
||||
inline RawPointer raw_ptr(Pointer const& p)
|
||||
{
|
||||
return raw_ptr<RawPointer>(p,std::is_same<RawPointer,Pointer>());
|
||||
return raw_ptr<RawPointer>(p,is_same<RawPointer,Pointer>());
|
||||
}
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,11 +14,11 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <algorithm>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/auto_space.hpp>
|
||||
#include <boost/multi_index/detail/rnd_index_ptr_array.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -44,10 +44,10 @@ class random_access_index_loader_base:private noncopyable
|
||||
{
|
||||
protected:
|
||||
typedef random_access_index_node_impl<
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
Allocator,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
> node_impl_type;
|
||||
typedef typename node_impl_type::pointer node_impl_pointer;
|
||||
typedef random_access_index_ptr_array<Allocator> ptr_array;
|
||||
@@ -93,7 +93,8 @@ protected:
|
||||
}
|
||||
|
||||
private:
|
||||
typedef allocator_size_type_t<Allocator> size_type;
|
||||
typedef allocator_traits<Allocator> alloc_traits;
|
||||
typedef typename alloc_traits::size_type size_type;
|
||||
|
||||
void preprocess()
|
||||
{
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,9 +14,9 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <algorithm>
|
||||
#include <boost/integer/common_factor_rt.hpp>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
#include <cstddef>
|
||||
#include <functional>
|
||||
@@ -30,16 +30,18 @@ namespace detail{
|
||||
template<typename Allocator>
|
||||
struct random_access_index_node_impl
|
||||
{
|
||||
typedef allocator_rebind_t<
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,random_access_index_node_impl
|
||||
> node_allocator;
|
||||
typedef allocator_pointer_t<node_allocator> pointer;
|
||||
typedef allocator_const_pointer_t<node_allocator> const_pointer;
|
||||
typedef allocator_difference_type_t<node_allocator> difference_type;
|
||||
typedef allocator_rebind_t<
|
||||
>::type node_allocator;
|
||||
typedef allocator_traits<node_allocator> node_alloc_traits;
|
||||
typedef typename node_alloc_traits::pointer pointer;
|
||||
typedef typename node_alloc_traits::const_pointer const_pointer;
|
||||
typedef typename node_alloc_traits::difference_type difference_type;
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,pointer
|
||||
> ptr_allocator;
|
||||
typedef allocator_pointer_t<ptr_allocator> ptr_pointer;
|
||||
>::type ptr_allocator;
|
||||
typedef allocator_traits<ptr_allocator> ptr_alloc_traits;
|
||||
typedef typename ptr_alloc_traits::pointer ptr_pointer;
|
||||
|
||||
ptr_pointer& up(){return up_;}
|
||||
ptr_pointer up()const{return up_;}
|
||||
@@ -167,25 +169,6 @@ struct random_access_index_node_impl
|
||||
}
|
||||
}
|
||||
|
||||
static ptr_pointer gather_nulls(
|
||||
ptr_pointer pbegin,ptr_pointer pend,ptr_pointer x)
|
||||
{
|
||||
for(ptr_pointer p=pbegin;p!=x;++p){
|
||||
if(*p){
|
||||
*pbegin=*p;
|
||||
(*pbegin)->up()=pbegin;
|
||||
++pbegin;
|
||||
}
|
||||
}
|
||||
for(ptr_pointer p=pend;p!=x;){
|
||||
if(*--p){
|
||||
*--pend=*p;
|
||||
(*pend)->up()=pend;
|
||||
}
|
||||
}
|
||||
return pbegin;
|
||||
}
|
||||
|
||||
private:
|
||||
ptr_pointer up_;
|
||||
};
|
||||
@@ -193,17 +176,17 @@ private:
|
||||
template<typename Super>
|
||||
struct random_access_index_node_trampoline:
|
||||
random_access_index_node_impl<
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
typename Super::allocator_type,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
>
|
||||
{
|
||||
typedef random_access_index_node_impl<
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
typename Super::allocator_type,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
> impl_type;
|
||||
};
|
||||
|
||||
@@ -215,18 +198,11 @@ private:
|
||||
typedef random_access_index_node_trampoline<Super> trampoline;
|
||||
|
||||
public:
|
||||
typedef typename trampoline::impl_type impl_type;
|
||||
typedef typename trampoline::pointer impl_pointer;
|
||||
typedef typename trampoline::const_pointer const_impl_pointer;
|
||||
typedef typename trampoline::difference_type difference_type;
|
||||
typedef typename trampoline::ptr_pointer impl_ptr_pointer;
|
||||
typedef allocator_rebind_t<
|
||||
typename trampoline::node_allocator,
|
||||
random_access_index_node> final_allocator_type;
|
||||
typedef allocator_pointer_t<
|
||||
final_allocator_type> pointer;
|
||||
typedef allocator_const_pointer_t<
|
||||
final_allocator_type> const_pointer;
|
||||
typedef typename trampoline::impl_type impl_type;
|
||||
typedef typename trampoline::pointer impl_pointer;
|
||||
typedef typename trampoline::const_pointer const_impl_pointer;
|
||||
typedef typename trampoline::difference_type difference_type;
|
||||
typedef typename trampoline::ptr_pointer impl_ptr_pointer;
|
||||
|
||||
impl_ptr_pointer& up(){return trampoline::up();}
|
||||
impl_ptr_pointer up()const{return trampoline::up();}
|
||||
@@ -261,25 +237,25 @@ public:
|
||||
|
||||
/* interoperability with rnd_node_iterator */
|
||||
|
||||
static void increment(pointer& x)
|
||||
static void increment(random_access_index_node*& x)
|
||||
{
|
||||
impl_pointer xi=x->impl();
|
||||
trampoline::increment(xi);
|
||||
x=pointer(from_impl(xi));
|
||||
x=from_impl(xi);
|
||||
}
|
||||
|
||||
static void decrement(pointer& x)
|
||||
static void decrement(random_access_index_node*& x)
|
||||
{
|
||||
impl_pointer xi=x->impl();
|
||||
trampoline::decrement(xi);
|
||||
x=pointer(from_impl(xi));
|
||||
x=from_impl(xi);
|
||||
}
|
||||
|
||||
static void advance(pointer& x,difference_type n)
|
||||
static void advance(random_access_index_node*& x,difference_type n)
|
||||
{
|
||||
impl_pointer xi=x->impl();
|
||||
trampoline::advance(xi,n);
|
||||
x=pointer(from_impl(xi));
|
||||
x=from_impl(xi);
|
||||
}
|
||||
|
||||
static difference_type distance(
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2015 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -83,7 +83,7 @@ template<typename Node,typename Allocator,typename Compare>
|
||||
void random_access_index_inplace_merge(
|
||||
const Allocator& al,
|
||||
random_access_index_ptr_array<Allocator>& ptrs,
|
||||
typename Node::impl_ptr_pointer first1,Compare comp)
|
||||
BOOST_DEDUCED_TYPENAME Node::impl_ptr_pointer first1,Compare comp)
|
||||
{
|
||||
typedef typename Node::value_type value_type;
|
||||
typedef typename Node::impl_pointer impl_pointer;
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,11 +14,11 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <algorithm>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/auto_space.hpp>
|
||||
#include <boost/multi_index/detail/rnd_index_node.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -32,21 +32,20 @@ template<typename Allocator>
|
||||
class random_access_index_ptr_array:private noncopyable
|
||||
{
|
||||
typedef random_access_index_node_impl<
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
Allocator,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
> node_impl_type;
|
||||
|
||||
public:
|
||||
typedef typename node_impl_type::pointer value_type;
|
||||
typedef allocator_rebind_t<
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,value_type
|
||||
> value_allocator;
|
||||
typedef allocator_pointer_t<
|
||||
value_allocator> pointer;
|
||||
typedef allocator_size_type_t<
|
||||
value_allocator> size_type;
|
||||
>::type value_allocator;
|
||||
typedef allocator_traits<value_allocator> alloc_traits;
|
||||
typedef typename alloc_traits::pointer pointer;
|
||||
typedef typename alloc_traits::size_type size_type;
|
||||
|
||||
random_access_index_ptr_array(
|
||||
const Allocator& al,value_type end_,size_type sz):
|
||||
@@ -111,14 +110,6 @@ public:
|
||||
spc.swap(x.spc);
|
||||
}
|
||||
|
||||
template<typename BoolConstant>
|
||||
void swap(random_access_index_ptr_array& x,BoolConstant swap_allocators)
|
||||
{
|
||||
std::swap(size_,x.size_);
|
||||
std::swap(capacity_,x.capacity_);
|
||||
spc.swap(x.spc,swap_allocators);
|
||||
}
|
||||
|
||||
private:
|
||||
size_type size_;
|
||||
size_type capacity_;
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,11 +14,11 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
#include <boost/operators.hpp>
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/serialization/nvp.hpp>
|
||||
#include <boost/serialization/split_member.hpp>
|
||||
#endif
|
||||
|
||||
namespace boost{
|
||||
@@ -77,27 +77,23 @@ public:
|
||||
* see explanation in safe_mode_iterator notes in safe_mode.hpp.
|
||||
*/
|
||||
|
||||
template<class Archive>
|
||||
void serialize(Archive& ar,const unsigned int version)
|
||||
{
|
||||
core::split_member(ar,*this,version);
|
||||
}
|
||||
BOOST_SERIALIZATION_SPLIT_MEMBER()
|
||||
|
||||
typedef typename Node::base_type node_base_type;
|
||||
|
||||
template<class Archive>
|
||||
void save(Archive& ar,const unsigned int)const
|
||||
{
|
||||
node_base_type* bnode=get_node();
|
||||
ar<<core::make_nvp("pointer",bnode);
|
||||
node_base_type* bnode=node;
|
||||
ar<<serialization::make_nvp("pointer",bnode);
|
||||
}
|
||||
|
||||
template<class Archive>
|
||||
void load(Archive& ar,const unsigned int)
|
||||
{
|
||||
node_base_type* bnode;
|
||||
ar>>core::make_nvp("pointer",bnode);
|
||||
node=typename Node::pointer(static_cast<Node*>(bnode));
|
||||
ar>>serialization::make_nvp("pointer",bnode);
|
||||
node=static_cast<Node*>(bnode);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -105,10 +101,10 @@ public:
|
||||
|
||||
typedef Node node_type;
|
||||
|
||||
Node* get_node()const{return raw_ptr<Node*>(node);}
|
||||
Node* get_node()const{return node;}
|
||||
|
||||
private:
|
||||
typename Node::pointer node;
|
||||
Node* node;
|
||||
};
|
||||
|
||||
template<typename Node>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2018 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,9 +15,8 @@
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/pointer_traits.hpp>
|
||||
#include <boost/mp11/function.hpp>
|
||||
#include <boost/mpl/and.hpp>
|
||||
#include <boost/multi_index/detail/promotes_arg.hpp>
|
||||
#include <type_traits>
|
||||
#include <utility>
|
||||
|
||||
namespace boost{
|
||||
@@ -46,7 +45,7 @@ ranked_node_size(Pointer x)
|
||||
|
||||
template<typename Pointer>
|
||||
inline Pointer ranked_index_nth(
|
||||
typename ranked_node_size_type<Pointer>::type n,Pointer end_)
|
||||
BOOST_DEDUCED_TYPENAME ranked_node_size_type<Pointer>::type n,Pointer end_)
|
||||
{
|
||||
typedef typename ranked_node_size_type<Pointer>::type size_type;
|
||||
|
||||
@@ -97,7 +96,7 @@ inline typename Node::size_type ranked_index_find_rank(
|
||||
|
||||
return ranked_index_find_rank(
|
||||
top,y,key,x,comp,
|
||||
mp11::mp_and<
|
||||
mpl::and_<
|
||||
promotes_1st_arg<CompatibleCompare,CompatibleKey,key_type>,
|
||||
promotes_2nd_arg<CompatibleCompare,key_type,CompatibleKey> >());
|
||||
}
|
||||
@@ -108,10 +107,10 @@ template<
|
||||
>
|
||||
inline typename Node::size_type ranked_index_find_rank(
|
||||
Node* top,Node* y,const KeyFromValue& key,
|
||||
const typename KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,std::true_type)
|
||||
const BOOST_DEDUCED_TYPENAME KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,mpl::true_)
|
||||
{
|
||||
return ranked_index_find_rank(top,y,key,x,comp,std::false_type());
|
||||
return ranked_index_find_rank(top,y,key,x,comp,mpl::false_());
|
||||
}
|
||||
|
||||
template<
|
||||
@@ -120,7 +119,7 @@ template<
|
||||
>
|
||||
inline typename Node::size_type ranked_index_find_rank(
|
||||
Node* top,Node* y,const KeyFromValue& key,const CompatibleKey& x,
|
||||
const CompatibleCompare& comp,std::false_type)
|
||||
const CompatibleCompare& comp,mpl::false_)
|
||||
{
|
||||
typedef typename Node::size_type size_type;
|
||||
|
||||
@@ -163,10 +162,10 @@ template<
|
||||
>
|
||||
inline typename Node::size_type ranked_index_lower_bound_rank(
|
||||
Node* top,Node* y,const KeyFromValue& key,
|
||||
const typename KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,std::true_type)
|
||||
const BOOST_DEDUCED_TYPENAME KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,mpl::true_)
|
||||
{
|
||||
return ranked_index_lower_bound_rank(top,y,key,x,comp,std::false_type());
|
||||
return ranked_index_lower_bound_rank(top,y,key,x,comp,mpl::false_());
|
||||
}
|
||||
|
||||
template<
|
||||
@@ -175,7 +174,7 @@ template<
|
||||
>
|
||||
inline typename Node::size_type ranked_index_lower_bound_rank(
|
||||
Node* top,Node* y,const KeyFromValue& key,const CompatibleKey& x,
|
||||
const CompatibleCompare& comp,std::false_type)
|
||||
const CompatibleCompare& comp,mpl::false_)
|
||||
{
|
||||
typedef typename Node::size_type size_type;
|
||||
|
||||
@@ -216,10 +215,10 @@ template<
|
||||
>
|
||||
inline typename Node::size_type ranked_index_upper_bound_rank(
|
||||
Node* top,Node* y,const KeyFromValue& key,
|
||||
const typename KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,std::true_type)
|
||||
const BOOST_DEDUCED_TYPENAME KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,mpl::true_)
|
||||
{
|
||||
return ranked_index_upper_bound_rank(top,y,key,x,comp,std::false_type());
|
||||
return ranked_index_upper_bound_rank(top,y,key,x,comp,mpl::false_());
|
||||
}
|
||||
|
||||
template<
|
||||
@@ -228,7 +227,7 @@ template<
|
||||
>
|
||||
inline typename Node::size_type ranked_index_upper_bound_rank(
|
||||
Node* top,Node* y,const KeyFromValue& key,const CompatibleKey& x,
|
||||
const CompatibleCompare& comp,std::false_type)
|
||||
const CompatibleCompare& comp,mpl::false_)
|
||||
{
|
||||
typedef typename Node::size_type size_type;
|
||||
|
||||
@@ -261,7 +260,7 @@ ranked_index_equal_range_rank(
|
||||
|
||||
return ranked_index_equal_range_rank(
|
||||
top,y,key,x,comp,
|
||||
mp11::mp_and<
|
||||
mpl::and_<
|
||||
promotes_1st_arg<CompatibleCompare,CompatibleKey,key_type>,
|
||||
promotes_2nd_arg<CompatibleCompare,key_type,CompatibleKey> >());
|
||||
}
|
||||
@@ -273,10 +272,10 @@ template<
|
||||
inline std::pair<typename Node::size_type,typename Node::size_type>
|
||||
ranked_index_equal_range_rank(
|
||||
Node* top,Node* y,const KeyFromValue& key,
|
||||
const typename KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,std::true_type)
|
||||
const BOOST_DEDUCED_TYPENAME KeyFromValue::result_type& x,
|
||||
const CompatibleCompare& comp,mpl::true_)
|
||||
{
|
||||
return ranked_index_equal_range_rank(top,y,key,x,comp,std::false_type());
|
||||
return ranked_index_equal_range_rank(top,y,key,x,comp,mpl::false_());
|
||||
}
|
||||
|
||||
template<
|
||||
@@ -286,11 +285,11 @@ template<
|
||||
inline std::pair<typename Node::size_type,typename Node::size_type>
|
||||
ranked_index_equal_range_rank(
|
||||
Node* top,Node* y,const KeyFromValue& key,const CompatibleKey& x,
|
||||
const CompatibleCompare& comp,std::false_type)
|
||||
const CompatibleCompare& comp,mpl::false_)
|
||||
{
|
||||
typedef typename Node::size_type size_type;
|
||||
|
||||
if(!top)return std::pair<size_type,size_type>((size_type)0,(size_type)0);
|
||||
if(!top)return std::pair<size_type,size_type>(0,0);
|
||||
|
||||
size_type s=top->impl()->size;
|
||||
|
||||
@@ -305,12 +304,12 @@ ranked_index_equal_range_rank(
|
||||
}
|
||||
else{
|
||||
return std::pair<size_type,size_type>(
|
||||
(size_type)(s-top->impl()->size+
|
||||
s-top->impl()->size+
|
||||
ranked_index_lower_bound_rank(
|
||||
Node::from_impl(top->left()),top,key,x,comp,std::false_type())),
|
||||
(size_type)(s-ranked_node_size(top->right())+
|
||||
Node::from_impl(top->left()),top,key,x,comp,mpl::false_()),
|
||||
s-ranked_node_size(top->right())+
|
||||
ranked_index_upper_bound_rank(
|
||||
Node::from_impl(top->right()),y,key,x,comp,std::false_type())));
|
||||
Node::from_impl(top->right()),y,key,x,comp,mpl::false_()));
|
||||
}
|
||||
}while(top);
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -15,9 +15,9 @@
|
||||
|
||||
/* Safe mode machinery, in the spirit of Cay Hortmann's "Safe STL"
|
||||
* (http://www.horstmann.com/safestl.html).
|
||||
* In this mode, containers have to redefine their iterators as
|
||||
* safe_iterator<base_iterator> and keep a tracking object member of
|
||||
* type safe_container<safe_iterator<base_iterator> >. These classes provide
|
||||
* In this mode, containers of type Container are derived from
|
||||
* safe_container<Container>, and their corresponding iterators
|
||||
* are wrapped with safe_iterator. These classes provide
|
||||
* an internal record of which iterators are at a given moment associated
|
||||
* to a given container, and properly mark the iterators as invalid
|
||||
* when the container gets destroyed.
|
||||
@@ -80,11 +80,6 @@
|
||||
safe_mode::check_is_owner(it,cont), \
|
||||
safe_mode::not_owner);
|
||||
|
||||
#define BOOST_MULTI_INDEX_CHECK_BELONGS_IN_SOME_INDEX(it,cont) \
|
||||
BOOST_MULTI_INDEX_SAFE_MODE_ASSERT( \
|
||||
safe_mode::check_belongs_in_some_index(it,cont), \
|
||||
safe_mode::not_owner);
|
||||
|
||||
#define BOOST_MULTI_INDEX_CHECK_SAME_OWNER(it0,it1) \
|
||||
BOOST_MULTI_INDEX_SAFE_MODE_ASSERT( \
|
||||
safe_mode::check_same_owner(it0,it1), \
|
||||
@@ -110,28 +105,22 @@
|
||||
safe_mode::check_different_container(cont0,cont1), \
|
||||
safe_mode::same_container);
|
||||
|
||||
#define BOOST_MULTI_INDEX_CHECK_EQUAL_ALLOCATORS(cont0,cont1) \
|
||||
BOOST_MULTI_INDEX_SAFE_MODE_ASSERT( \
|
||||
safe_mode::check_equal_allocators(cont0,cont1), \
|
||||
safe_mode::unequal_allocators);
|
||||
|
||||
#if defined(BOOST_MULTI_INDEX_ENABLE_SAFE_MODE)
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <algorithm>
|
||||
#include <boost/core/addressof.hpp>
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/multi_index/detail/any_container_view.hpp>
|
||||
#include <boost/detail/iterator.hpp>
|
||||
#include <boost/multi_index/detail/access_specifier.hpp>
|
||||
#include <boost/multi_index/detail/iter_adaptor.hpp>
|
||||
#include <boost/multi_index/safe_mode_errors.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
#include <boost/noncopyable.hpp>
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/serialization/split_member.hpp>
|
||||
#include <boost/serialization/version.hpp>
|
||||
#endif
|
||||
|
||||
#if defined(BOOST_HAS_THREADS)
|
||||
#include <boost/smart_ptr/detail/lightweight_mutex.hpp>
|
||||
#include <boost/multi_index/detail/scoped_bilock.hpp>
|
||||
#include <boost/detail/lightweight_mutex.hpp>
|
||||
#endif
|
||||
|
||||
namespace boost{
|
||||
@@ -169,29 +158,18 @@ inline bool check_decrementable_iterator(const Iterator& it)
|
||||
return (it.valid()&&it!=it.owner()->begin())||it.unchecked();
|
||||
}
|
||||
|
||||
template<typename Iterator,typename Container>
|
||||
template<typename Iterator>
|
||||
inline bool check_is_owner(
|
||||
const Iterator& it,const Container& cont)
|
||||
const Iterator& it,const typename Iterator::container_type& cont)
|
||||
{
|
||||
return (it.valid()&&
|
||||
it.owner()->container()==cont.end().owner()->container())
|
||||
||it.unchecked();
|
||||
return (it.valid()&&it.owner()==&cont)||it.unchecked();
|
||||
}
|
||||
|
||||
template<typename Iterator,typename MultiIndexContainer>
|
||||
inline bool check_belongs_in_some_index(
|
||||
const Iterator& it,const MultiIndexContainer& cont)
|
||||
{
|
||||
return (it.valid()&&it.owner()->end().get_node()==cont.end().get_node())
|
||||
||it.unchecked();
|
||||
}
|
||||
|
||||
template<typename Iterator>
|
||||
inline bool check_same_owner(const Iterator& it0,const Iterator& it1)
|
||||
{
|
||||
return (it0.valid()&&it1.valid()&&
|
||||
it0.owner()->container()==it1.owner()->container())
|
||||
||it0.unchecked()||it1.unchecked();
|
||||
return (it0.valid()&&it1.valid()&&it0.owner()==it1.owner())||
|
||||
it0.unchecked()||it1.unchecked();
|
||||
}
|
||||
|
||||
template<typename Iterator>
|
||||
@@ -235,28 +213,6 @@ inline bool check_outside_range(
|
||||
return true;
|
||||
}
|
||||
|
||||
template<typename Iterator1,typename Iterator2>
|
||||
inline bool check_outside_range(
|
||||
const Iterator1& it,const Iterator2& it0,const Iterator2& it1)
|
||||
{
|
||||
if(it.valid()&&it!=it.owner()->end()&&it0.valid()){
|
||||
Iterator2 last=it0.owner()->end();
|
||||
bool found=false;
|
||||
|
||||
Iterator2 first=it0;
|
||||
for(;first!=last;++first){
|
||||
if(first==it1)break;
|
||||
|
||||
/* crucial that this check goes after previous break */
|
||||
|
||||
if(boost::addressof(*first)==boost::addressof(*it))found=true;
|
||||
}
|
||||
if(first!=it1)return false;
|
||||
return !found;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
template<typename Iterator,typename Difference>
|
||||
inline bool check_in_bounds(const Iterator& it,Difference n)
|
||||
{
|
||||
@@ -273,33 +229,42 @@ inline bool check_different_container(
|
||||
return &cont0!=&cont1;
|
||||
}
|
||||
|
||||
template<typename Container1,typename Container2>
|
||||
inline bool check_different_container(const Container1&,const Container2&)
|
||||
/* Invalidates all iterators equivalent to that given. Safe containers
|
||||
* must call this when deleting elements: the safe mode framework cannot
|
||||
* perform this operation automatically without outside help.
|
||||
*/
|
||||
|
||||
template<typename Iterator>
|
||||
inline void detach_equivalent_iterators(Iterator& it)
|
||||
{
|
||||
return true;
|
||||
if(it.valid()){
|
||||
{
|
||||
#if defined(BOOST_HAS_THREADS)
|
||||
boost::detail::lightweight_mutex::scoped_lock lock(it.cont->mutex);
|
||||
#endif
|
||||
|
||||
Iterator *prev_,*next_;
|
||||
for(
|
||||
prev_=static_cast<Iterator*>(&it.cont->header);
|
||||
(next_=static_cast<Iterator*>(prev_->next))!=0;){
|
||||
if(next_!=&it&&*next_==it){
|
||||
prev_->next=next_->next;
|
||||
next_->cont=0;
|
||||
}
|
||||
else prev_=next_;
|
||||
}
|
||||
}
|
||||
it.detach();
|
||||
}
|
||||
}
|
||||
|
||||
template<typename Container0,typename Container1>
|
||||
inline bool check_equal_allocators(
|
||||
const Container0& cont0,const Container1& cont1)
|
||||
{
|
||||
return cont0.get_allocator()==cont1.get_allocator();
|
||||
}
|
||||
template<typename Container> class safe_container; /* fwd decl. */
|
||||
|
||||
/* fwd decls */
|
||||
} /* namespace multi_index::safe_mode */
|
||||
|
||||
template<typename Container> class safe_container;
|
||||
template<typename Iterator> void detach_equivalent_iterators(Iterator&);
|
||||
namespace detail{
|
||||
|
||||
namespace safe_mode_detail{
|
||||
|
||||
/* fwd decls */
|
||||
|
||||
class safe_container_base;
|
||||
template<typename Dst,typename Iterator>
|
||||
void transfer_equivalent_iterators(Dst&,Iterator,boost::true_type);
|
||||
template<typename Dst,typename Iterator>
|
||||
inline void transfer_equivalent_iterators(Dst&,Iterator&,boost::false_type);
|
||||
class safe_container_base; /* fwd decl. */
|
||||
|
||||
class safe_iterator_base
|
||||
{
|
||||
@@ -348,15 +313,14 @@ protected:
|
||||
|
||||
const safe_container_base* owner()const{return cont;}
|
||||
|
||||
private:
|
||||
BOOST_MULTI_INDEX_PRIVATE_IF_MEMBER_TEMPLATE_FRIENDS:
|
||||
friend class safe_container_base;
|
||||
template<typename>
|
||||
friend class safe_mode::safe_container;
|
||||
template<typename Iterator>
|
||||
friend void safe_mode::detach_equivalent_iterators(Iterator&);
|
||||
template<typename Dst,typename Iterator>
|
||||
friend void safe_mode_detail::transfer_equivalent_iterators(
|
||||
Dst&,Iterator,boost::true_type);
|
||||
|
||||
#if !defined(BOOST_NO_MEMBER_TEMPLATE_FRIENDS)
|
||||
template<typename> friend class safe_mode::safe_container;
|
||||
template<typename Iterator> friend
|
||||
void safe_mode::detach_equivalent_iterators(Iterator&);
|
||||
#endif
|
||||
|
||||
inline void attach(safe_container_base* cont_);
|
||||
|
||||
@@ -370,13 +334,13 @@ class safe_container_base:private noncopyable
|
||||
public:
|
||||
safe_container_base(){}
|
||||
|
||||
protected:
|
||||
BOOST_MULTI_INDEX_PROTECTED_IF_MEMBER_TEMPLATE_FRIENDS:
|
||||
friend class safe_iterator_base;
|
||||
template<typename Iterator>
|
||||
friend void safe_mode::detach_equivalent_iterators(Iterator&);
|
||||
template<typename Dst,typename Iterator>
|
||||
friend void safe_mode_detail::transfer_equivalent_iterators(
|
||||
Dst&,Iterator,boost::true_type);
|
||||
|
||||
#if !defined(BOOST_NO_MEMBER_TEMPLATE_FRIENDS)
|
||||
template<typename Iterator> friend
|
||||
void safe_mode::detach_equivalent_iterators(Iterator&);
|
||||
#endif
|
||||
|
||||
~safe_container_base()
|
||||
{
|
||||
@@ -430,38 +394,42 @@ void safe_iterator_base::detach()
|
||||
}
|
||||
}
|
||||
|
||||
} /* namespace multi_index::safe_mode::safe_mode_detail */
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
namespace safe_mode{
|
||||
|
||||
/* In order to enable safe mode on a container:
|
||||
* - The container must keep a member of type safe_container<iterator>,
|
||||
* - The container must derive from safe_container<container_type>,
|
||||
* - iterators must be generated via safe_iterator, which adapts a
|
||||
* preexistent unsafe iterator class. safe_iterators are passed the
|
||||
* address of the previous safe_container member at construction time.
|
||||
* preexistent unsafe iterator class.
|
||||
*/
|
||||
|
||||
template<typename Iterator>
|
||||
template<typename Container>
|
||||
class safe_container;
|
||||
|
||||
template<typename Iterator,typename Container>
|
||||
class safe_iterator:
|
||||
public detail::iter_adaptor<safe_iterator<Iterator>,Iterator>,
|
||||
public safe_mode_detail::safe_iterator_base
|
||||
public detail::iter_adaptor<safe_iterator<Iterator,Container>,Iterator>,
|
||||
public detail::safe_iterator_base
|
||||
{
|
||||
typedef detail::iter_adaptor<safe_iterator,Iterator> super;
|
||||
typedef safe_mode_detail::safe_iterator_base safe_super;
|
||||
typedef detail::safe_iterator_base safe_super;
|
||||
|
||||
public:
|
||||
typedef Container container_type;
|
||||
typedef typename Iterator::reference reference;
|
||||
typedef typename Iterator::difference_type difference_type;
|
||||
|
||||
safe_iterator(){}
|
||||
explicit safe_iterator(safe_container<safe_iterator>* cont_):
|
||||
explicit safe_iterator(safe_container<container_type>* cont_):
|
||||
safe_super(cont_){}
|
||||
template<typename T0>
|
||||
safe_iterator(const T0& t0,safe_container<safe_iterator>* cont_):
|
||||
safe_iterator(const T0& t0,safe_container<container_type>* cont_):
|
||||
super(Iterator(t0)),safe_super(cont_){}
|
||||
template<typename T0,typename T1>
|
||||
safe_iterator(
|
||||
const T0& t0,const T1& t1,safe_container<safe_iterator>* cont_):
|
||||
const T0& t0,const T1& t1,safe_container<container_type>* cont_):
|
||||
super(Iterator(t0,t1)),safe_super(cont_){}
|
||||
safe_iterator(const safe_iterator& x):super(x),safe_super(x){}
|
||||
|
||||
safe_iterator& operator=(const safe_iterator& x)
|
||||
{
|
||||
@@ -471,11 +439,12 @@ public:
|
||||
return *this;
|
||||
}
|
||||
|
||||
const safe_container<safe_iterator>* owner()const
|
||||
const container_type* owner()const
|
||||
{
|
||||
return
|
||||
static_cast<const safe_container<safe_iterator>*>(
|
||||
this->safe_super::owner());
|
||||
static_cast<const container_type*>(
|
||||
static_cast<const safe_container<container_type>*>(
|
||||
this->safe_super::owner()));
|
||||
}
|
||||
|
||||
/* get_node is not to be used by the user */
|
||||
@@ -548,11 +517,7 @@ private:
|
||||
|
||||
friend class boost::serialization::access;
|
||||
|
||||
template<class Archive>
|
||||
void serialize(Archive& ar,const unsigned int version)
|
||||
{
|
||||
core::split_member(ar,*this,version);
|
||||
}
|
||||
BOOST_SERIALIZATION_SPLIT_MEMBER()
|
||||
|
||||
template<class Archive>
|
||||
void save(Archive& ar,const unsigned int version)const
|
||||
@@ -570,28 +535,21 @@ private:
|
||||
#endif
|
||||
};
|
||||
|
||||
template<typename Iterator>
|
||||
class safe_container:public safe_mode_detail::safe_container_base
|
||||
template<typename Container>
|
||||
class safe_container:public detail::safe_container_base
|
||||
{
|
||||
typedef safe_mode_detail::safe_container_base super;
|
||||
|
||||
detail::any_container_view<Iterator> view;
|
||||
typedef detail::safe_container_base super;
|
||||
|
||||
public:
|
||||
template<typename Container>
|
||||
safe_container(const Container& c):view(c){}
|
||||
|
||||
const void* container()const{return view.container();}
|
||||
Iterator begin()const{return view.begin();}
|
||||
Iterator end()const{return view.end();}
|
||||
|
||||
void detach_dereferenceable_iterators()
|
||||
{
|
||||
Iterator end_=view.end();
|
||||
Iterator *prev_,*next_;
|
||||
typedef typename Container::iterator iterator;
|
||||
|
||||
iterator end_=static_cast<Container*>(this)->end();
|
||||
iterator *prev_,*next_;
|
||||
for(
|
||||
prev_=static_cast<Iterator*>(&this->header);
|
||||
(next_=static_cast<Iterator*>(prev_->next))!=0;){
|
||||
prev_=static_cast<iterator*>(&this->header);
|
||||
(next_=static_cast<iterator*>(prev_->next))!=0;){
|
||||
if(*next_!=end_){
|
||||
prev_->next=next_->next;
|
||||
next_->cont=0;
|
||||
@@ -600,102 +558,21 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
void swap(safe_container<Iterator>& x)
|
||||
void swap(safe_container<Container>& x)
|
||||
{
|
||||
super::swap(x);
|
||||
}
|
||||
};
|
||||
|
||||
/* Invalidates all iterators equivalent to that given. Safe containers
|
||||
* must call this when deleting elements: the safe mode framework cannot
|
||||
* perform this operation automatically without outside help.
|
||||
*/
|
||||
|
||||
template<typename Iterator>
|
||||
inline void detach_equivalent_iterators(Iterator& it)
|
||||
{
|
||||
if(it.valid()){
|
||||
{
|
||||
#if defined(BOOST_HAS_THREADS)
|
||||
boost::detail::lightweight_mutex::scoped_lock lock(it.cont->mutex);
|
||||
#endif
|
||||
|
||||
Iterator *prev_,*next_;
|
||||
for(
|
||||
prev_=static_cast<Iterator*>(&it.cont->header);
|
||||
(next_=static_cast<Iterator*>(prev_->next))!=0;){
|
||||
if(next_!=&it&&*next_==it){
|
||||
prev_->next=next_->next;
|
||||
next_->cont=0;
|
||||
}
|
||||
else prev_=next_;
|
||||
}
|
||||
}
|
||||
it.detach();
|
||||
}
|
||||
}
|
||||
|
||||
/* Transfers iterators equivalent to that given to Dst, if that container has
|
||||
* the same iterator type; otherwise, detaches them.
|
||||
*/
|
||||
|
||||
template<typename Dst,typename Iterator>
|
||||
inline void transfer_equivalent_iterators(Dst& dst,Iterator& i)
|
||||
{
|
||||
safe_mode_detail::transfer_equivalent_iterators(
|
||||
dst,i,boost::is_same<Iterator,typename Dst::iterator>());
|
||||
}
|
||||
|
||||
namespace safe_mode_detail{
|
||||
|
||||
template<typename Dst,typename Iterator>
|
||||
inline void transfer_equivalent_iterators(
|
||||
Dst& dst,Iterator it,boost::true_type /* same iterator type */)
|
||||
{
|
||||
if(it.valid()){
|
||||
{
|
||||
safe_container_base* cont_=dst.end().cont;
|
||||
|
||||
#if defined(BOOST_HAS_THREADS)
|
||||
detail::scoped_bilock<boost::detail::lightweight_mutex>
|
||||
scoped_bilock(it.cont->mutex,cont_->mutex);
|
||||
#endif
|
||||
|
||||
Iterator *prev_,*next_;
|
||||
for(
|
||||
prev_=static_cast<Iterator*>(&it.cont->header);
|
||||
(next_=static_cast<Iterator*>(prev_->next))!=0;){
|
||||
if(next_!=&it&&*next_==it){
|
||||
prev_->next=next_->next;
|
||||
next_->cont=cont_;
|
||||
next_->next=cont_->header.next;
|
||||
cont_->header.next=next_;
|
||||
}
|
||||
else prev_=next_;
|
||||
}
|
||||
}
|
||||
/* nothing to do with it, was passed by value and will die now */
|
||||
}
|
||||
}
|
||||
|
||||
template<typename Dst,typename Iterator>
|
||||
inline void transfer_equivalent_iterators(
|
||||
Dst&,Iterator& it,boost::false_type /* same iterator type */)
|
||||
{
|
||||
detach_equivalent_iterators(it);
|
||||
}
|
||||
|
||||
} /* namespace multi_index::safe_mode::safe_mode_detail */
|
||||
|
||||
} /* namespace multi_index::safe_mode */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_DISABLE_SERIALIZATION)
|
||||
namespace serialization{
|
||||
template<typename Iterator>
|
||||
template<typename Iterator,typename Container>
|
||||
struct version<
|
||||
boost::multi_index::safe_mode::safe_iterator<Iterator>
|
||||
boost::multi_index::safe_mode::safe_iterator<Iterator,Container>
|
||||
>
|
||||
{
|
||||
BOOST_STATIC_CONSTANT(
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -13,8 +13,8 @@
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/core/no_exceptions_support.hpp>
|
||||
#include <boost/mp11/utility.hpp>
|
||||
#include <boost/detail/no_exceptions_support.hpp>
|
||||
#include <boost/mpl/if.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -120,7 +120,7 @@ struct null_guard : public scope_guard_impl_base
|
||||
template< bool cond, class T >
|
||||
struct null_guard_return
|
||||
{
|
||||
typedef mp11::mp_if_c<cond,T,null_guard> type;
|
||||
typedef typename boost::mpl::if_c<cond,T,null_guard>::type type;
|
||||
};
|
||||
|
||||
template<typename F>
|
||||
|
||||
@@ -1,70 +0,0 @@
|
||||
/* Copyright 2003-2022 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_SCOPED_BILOCK_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_SCOPED_BILOCK_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/core/noncopyable.hpp>
|
||||
#include <boost/type_traits/aligned_storage.hpp>
|
||||
#include <boost/type_traits/alignment_of.hpp>
|
||||
#include <functional>
|
||||
#include <new>
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
/* Locks/unlocks two RAII-lockable mutexes taking care that locking is done in
|
||||
* a deadlock-avoiding global order and no double locking happens when the two
|
||||
* mutexes are the same.
|
||||
*/
|
||||
|
||||
template<typename Mutex>
|
||||
class scoped_bilock:private noncopyable
|
||||
{
|
||||
public:
|
||||
scoped_bilock(Mutex& mutex1,Mutex& mutex2):mutex_eq(&mutex1==&mutex2)
|
||||
{
|
||||
bool mutex_lt=std::less<Mutex*>()(&mutex1,&mutex2);
|
||||
|
||||
::new (static_cast<void*>(&lock1)) scoped_lock(mutex_lt?mutex1:mutex2);
|
||||
if(!mutex_eq)
|
||||
::new (static_cast<void*>(&lock2)) scoped_lock(mutex_lt?mutex2:mutex1);
|
||||
}
|
||||
|
||||
~scoped_bilock()
|
||||
{
|
||||
reinterpret_cast<scoped_lock*>(&lock1)->~scoped_lock();
|
||||
if(!mutex_eq)
|
||||
reinterpret_cast<scoped_lock*>(&lock2)->~scoped_lock();
|
||||
}
|
||||
|
||||
private:
|
||||
typedef typename Mutex::scoped_lock scoped_lock;
|
||||
typedef typename aligned_storage<
|
||||
sizeof(scoped_lock),
|
||||
alignment_of<scoped_lock>::value
|
||||
>::type scoped_lock_space;
|
||||
|
||||
bool mutex_eq;
|
||||
scoped_lock_space lock1,lock2;
|
||||
};
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2026 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2019 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,8 +14,8 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/allocator_access.hpp>
|
||||
#include <algorithm>
|
||||
#include <boost/multi_index/detail/allocator_traits.hpp>
|
||||
#include <boost/multi_index/detail/raw_ptr.hpp>
|
||||
|
||||
namespace boost{
|
||||
@@ -29,14 +29,13 @@ namespace detail{
|
||||
template<typename Allocator>
|
||||
struct sequenced_index_node_impl
|
||||
{
|
||||
typedef allocator_rebind_t<
|
||||
typedef typename rebind_alloc_for<
|
||||
Allocator,sequenced_index_node_impl
|
||||
> node_allocator;
|
||||
typedef allocator_pointer_t<node_allocator> pointer;
|
||||
typedef allocator_const_pointer_t<
|
||||
node_allocator> const_pointer;
|
||||
typedef allocator_difference_type_t<
|
||||
node_allocator> difference_type;
|
||||
>::type node_allocator;
|
||||
typedef allocator_traits<node_allocator> alloc_traits;
|
||||
typedef typename alloc_traits::pointer pointer;
|
||||
typedef typename alloc_traits::const_pointer const_pointer;
|
||||
typedef typename alloc_traits::difference_type difference_type;
|
||||
|
||||
pointer& prior(){return prior_;}
|
||||
pointer prior()const{return prior_;}
|
||||
@@ -133,17 +132,17 @@ private:
|
||||
template<typename Super>
|
||||
struct sequenced_index_node_trampoline:
|
||||
sequenced_index_node_impl<
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
typename Super::allocator_type,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
>
|
||||
{
|
||||
typedef sequenced_index_node_impl<
|
||||
allocator_rebind_t<
|
||||
typename rebind_alloc_for<
|
||||
typename Super::allocator_type,
|
||||
char
|
||||
>
|
||||
>::type
|
||||
> impl_type;
|
||||
};
|
||||
|
||||
@@ -158,13 +157,6 @@ public:
|
||||
typedef typename trampoline::pointer impl_pointer;
|
||||
typedef typename trampoline::const_pointer const_impl_pointer;
|
||||
typedef typename trampoline::difference_type difference_type;
|
||||
typedef allocator_rebind_t<
|
||||
typename trampoline::node_allocator,
|
||||
sequenced_index_node> final_allocator_type;
|
||||
typedef allocator_pointer_t<
|
||||
final_allocator_type> pointer;
|
||||
typedef allocator_const_pointer_t<
|
||||
final_allocator_type> const_pointer;
|
||||
|
||||
impl_pointer& prior(){return trampoline::prior();}
|
||||
impl_pointer prior()const{return trampoline::prior();}
|
||||
@@ -199,24 +191,20 @@ public:
|
||||
raw_ptr<const impl_type*>(x)));
|
||||
}
|
||||
|
||||
/* Interoperability with bidir_node_iterator and index impl.
|
||||
* Templated for raw-pointer/non-raw-pointer versions.
|
||||
*/
|
||||
/* interoperability with bidir_node_iterator */
|
||||
|
||||
template<typename NodePtr>
|
||||
static void increment(NodePtr& x)
|
||||
static void increment(sequenced_index_node*& x)
|
||||
{
|
||||
impl_pointer xi=x->impl();
|
||||
trampoline::increment(xi);
|
||||
x=NodePtr(from_impl(xi));
|
||||
x=from_impl(xi);
|
||||
}
|
||||
|
||||
template<typename NodePtr>
|
||||
static void decrement(NodePtr& x)
|
||||
static void decrement(sequenced_index_node*& x)
|
||||
{
|
||||
impl_pointer xi=x->impl();
|
||||
trampoline::decrement(xi);
|
||||
x=NodePtr(from_impl(xi));
|
||||
x=from_impl(xi);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2016 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,7 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/no_exceptions_support.hpp>
|
||||
#include <boost/detail/no_exceptions_support.hpp>
|
||||
#include <boost/multi_index/detail/seq_index_node.hpp>
|
||||
#include <boost/limits.hpp>
|
||||
#include <boost/type_traits/aligned_storage.hpp>
|
||||
@@ -77,8 +77,8 @@ void sequenced_index_merge(SequencedIndex& x,SequencedIndex& y,Compare comp)
|
||||
|
||||
template<typename Node,typename Compare>
|
||||
void sequenced_index_collate(
|
||||
typename Node::impl_type* x,
|
||||
typename Node::impl_type* y,
|
||||
BOOST_DEDUCED_TYPENAME Node::impl_type* x,
|
||||
BOOST_DEDUCED_TYPENAME Node::impl_type* y,
|
||||
Compare comp)
|
||||
{
|
||||
typedef typename Node::impl_type impl_type;
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2023 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,8 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/core/serialization.hpp>
|
||||
#include <boost/serialization/split_member.hpp>
|
||||
#include <boost/serialization/version.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -41,11 +42,7 @@ struct serialization_version
|
||||
private:
|
||||
friend class boost::serialization::access;
|
||||
|
||||
template<class Archive>
|
||||
void serialize(Archive& ar,const unsigned int version)
|
||||
{
|
||||
core::split_member(ar,*this,version);
|
||||
}
|
||||
BOOST_SERIALIZATION_SPLIT_MEMBER()
|
||||
|
||||
template<class Archive>
|
||||
void save(Archive&,const unsigned int)const{}
|
||||
|
||||
@@ -1,62 +0,0 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_TYPE_LIST_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_TYPE_LIST_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#if defined(BOOST_MULTI_INDEX_ENABLE_MPL_SUPPORT)
|
||||
#define BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER \
|
||||
<boost/mpl/push_front.hpp>
|
||||
#include BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#undef BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#define BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER \
|
||||
<boost/mpl/vector.hpp>
|
||||
#include BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
#undef BOOST_MULTI_INDEX_BLOCK_BOOSTDEP_HEADER
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
using empty_type_list=mpl::vector0<>;
|
||||
|
||||
template<typename TypeList,typename T>
|
||||
using type_list_push_front=typename mpl::push_front<TypeList,T>::type;
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
#else
|
||||
#include <boost/mp11/list.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
using empty_type_list=mp11::mp_list<>;
|
||||
|
||||
template<typename TypeList,typename T>
|
||||
using type_list_push_front=mp11::mp_push_front<TypeList,T>;
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
#endif
|
||||
#endif
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,7 +14,7 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/mp11/integral.hpp>
|
||||
#include <boost/mpl/bool.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
@@ -64,8 +64,8 @@ struct uintptr_aux
|
||||
typedef uintptr_candidates<index>::type type;
|
||||
};
|
||||
|
||||
typedef mp11::mp_bool<uintptr_aux::has_uintptr_type> has_uintptr_type;
|
||||
typedef uintptr_aux::type uintptr_type;
|
||||
typedef mpl::bool_<uintptr_aux::has_uintptr_type> has_uintptr_type;
|
||||
typedef uintptr_aux::type uintptr_type;
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright 2003-2025 Joaquin M Lopez Munoz.
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
@@ -14,6 +14,7 @@
|
||||
#endif
|
||||
|
||||
#include <boost/config.hpp> /* keep it first to prevent nasty warns in MSVC */
|
||||
#include <boost/detail/workaround.hpp>
|
||||
|
||||
namespace boost{
|
||||
|
||||
|
||||
@@ -1,11 +0,0 @@
|
||||
/* Copyright 2003-2020 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#define BOOST_MULTI_INDEX_DETAIL_UNDEF_IF_CONSTEXPR_MACRO
|
||||
#include <boost/multi_index/detail/define_if_constexpr_macro.hpp>
|
||||
#undef BOOST_MULTI_INDEX_DETAIL_UNDEF_IF_CONSTEXPR_MACRO
|
||||
@@ -0,0 +1,247 @@
|
||||
/* Copyright 2003-2013 Joaquin M Lopez Munoz.
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
* http://www.boost.org/LICENSE_1_0.txt)
|
||||
*
|
||||
* See http://www.boost.org/libs/multi_index for library home page.
|
||||
*/
|
||||
|
||||
#ifndef BOOST_MULTI_INDEX_DETAIL_VARTEMPL_SUPPORT_HPP
|
||||
#define BOOST_MULTI_INDEX_DETAIL_VARTEMPL_SUPPORT_HPP
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
/* Utilities for emulation of variadic template functions. Variadic packs are
|
||||
* replaced by lists of BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS parameters:
|
||||
*
|
||||
* - typename... Args --> BOOST_MULTI_INDEX_TEMPLATE_PARAM_PACK
|
||||
* - Args&&... args --> BOOST_MULTI_INDEX_FUNCTION_PARAM_PACK
|
||||
* - std::forward<Args>(args)... --> BOOST_MULTI_INDEX_FORWARD_PARAM_PACK
|
||||
*
|
||||
* Forwarding emulated with Boost.Move. A template functions foo_imp
|
||||
* defined in such way accepts *exactly* BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS
|
||||
* arguments: variable number of arguments is emulated by providing a set of
|
||||
* overloads foo forwarding to foo_impl with
|
||||
*
|
||||
* BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL
|
||||
* BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL_EXTRA_ARG (initial extra arg)
|
||||
*
|
||||
* which fill the extra args with boost::multi_index::detail::noarg's.
|
||||
* boost::multi_index::detail::vartempl_placement_new works the opposite
|
||||
* way: it acceps a full a pointer x to Value and a
|
||||
* BOOST_MULTI_INDEX_FUNCTION_PARAM_PACK and forwards to
|
||||
* new(x) Value(args) where args is the argument pack after discarding
|
||||
* noarg's.
|
||||
*
|
||||
* Emulation decays to the real thing when the compiler supports variadic
|
||||
* templates and move semantics natively.
|
||||
*/
|
||||
|
||||
#include <boost/config.hpp>
|
||||
|
||||
#if defined(BOOST_NO_CXX11_RVALUE_REFERENCES)||\
|
||||
defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES)
|
||||
|
||||
#include <boost/move/core.hpp>
|
||||
#include <boost/move/utility.hpp>
|
||||
#include <boost/preprocessor/arithmetic/add.hpp>
|
||||
#include <boost/preprocessor/arithmetic/sub.hpp>
|
||||
#include <boost/preprocessor/cat.hpp>
|
||||
#include <boost/preprocessor/control/if.hpp>
|
||||
#include <boost/preprocessor/facilities/empty.hpp>
|
||||
#include <boost/preprocessor/facilities/intercept.hpp>
|
||||
#include <boost/preprocessor/logical/and.hpp>
|
||||
#include <boost/preprocessor/punctuation/comma.hpp>
|
||||
#include <boost/preprocessor/punctuation/comma_if.hpp>
|
||||
#include <boost/preprocessor/repetition/enum.hpp>
|
||||
#include <boost/preprocessor/repetition/enum_params.hpp>
|
||||
#include <boost/preprocessor/repetition/repeat_from_to.hpp>
|
||||
#include <boost/preprocessor/seq/elem.hpp>
|
||||
|
||||
#if !defined(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS)
|
||||
#define BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS 5
|
||||
#endif
|
||||
|
||||
#define BOOST_MULTI_INDEX_TEMPLATE_PARAM_PACK \
|
||||
BOOST_PP_ENUM_PARAMS( \
|
||||
BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,typename T)
|
||||
|
||||
#define BOOST_MULTI_INDEX_VARTEMPL_ARG(z,n,_) \
|
||||
BOOST_FWD_REF(BOOST_PP_CAT(T,n)) BOOST_PP_CAT(t,n)
|
||||
|
||||
#define BOOST_MULTI_INDEX_FUNCTION_PARAM_PACK \
|
||||
BOOST_PP_ENUM( \
|
||||
BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS, \
|
||||
BOOST_MULTI_INDEX_VARTEMPL_ARG,~)
|
||||
|
||||
#define BOOST_MULTI_INDEX_VARTEMPL_FORWARD_ARG(z,n,_) \
|
||||
boost::forward<BOOST_PP_CAT(T,n)>(BOOST_PP_CAT(t,n))
|
||||
|
||||
#define BOOST_MULTI_INDEX_FORWARD_PARAM_PACK \
|
||||
BOOST_PP_ENUM( \
|
||||
BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS, \
|
||||
BOOST_MULTI_INDEX_VARTEMPL_FORWARD_ARG,~)
|
||||
|
||||
namespace boost{namespace multi_index{namespace detail{
|
||||
struct noarg{};
|
||||
}}}
|
||||
|
||||
/* call vartempl function without args */
|
||||
|
||||
#define BOOST_MULTI_INDEX_NULL_PARAM_PACK \
|
||||
BOOST_PP_ENUM_PARAMS( \
|
||||
BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS, \
|
||||
boost::multi_index::detail::noarg() BOOST_PP_INTERCEPT)
|
||||
|
||||
#define BOOST_MULTI_INDEX_TEMPLATE_N(n) \
|
||||
template<BOOST_PP_ENUM_PARAMS(n,typename T)>
|
||||
|
||||
#define BOOST_MULTI_INDEX_TEMPLATE_0(n)
|
||||
|
||||
#define BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL_AUX(z,n,data) \
|
||||
BOOST_PP_IF(n, \
|
||||
BOOST_MULTI_INDEX_TEMPLATE_N, \
|
||||
BOOST_MULTI_INDEX_TEMPLATE_0)(n) \
|
||||
BOOST_PP_SEQ_ELEM(0,data) /* ret */ \
|
||||
BOOST_PP_SEQ_ELEM(1,data) /* name_from */ ( \
|
||||
BOOST_PP_ENUM(n,BOOST_MULTI_INDEX_VARTEMPL_ARG,~)) \
|
||||
{ \
|
||||
return BOOST_PP_SEQ_ELEM(2,data) /* name_to */ ( \
|
||||
BOOST_PP_ENUM(n,BOOST_MULTI_INDEX_VARTEMPL_FORWARD_ARG,~) \
|
||||
BOOST_PP_COMMA_IF( \
|
||||
BOOST_PP_AND( \
|
||||
n,BOOST_PP_SUB(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,n))) \
|
||||
BOOST_PP_ENUM_PARAMS( \
|
||||
BOOST_PP_SUB(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,n), \
|
||||
boost::multi_index::detail::noarg() BOOST_PP_INTERCEPT) \
|
||||
); \
|
||||
}
|
||||
|
||||
#define BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL( \
|
||||
ret,name_from,name_to) \
|
||||
BOOST_PP_REPEAT_FROM_TO( \
|
||||
0,BOOST_PP_ADD(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,1), \
|
||||
BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL_AUX, \
|
||||
(ret)(name_from)(name_to))
|
||||
|
||||
#define BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL_EXTRA_ARG_AUX( \
|
||||
z,n,data) \
|
||||
BOOST_PP_IF(n, \
|
||||
BOOST_MULTI_INDEX_TEMPLATE_N, \
|
||||
BOOST_MULTI_INDEX_TEMPLATE_0)(n) \
|
||||
BOOST_PP_SEQ_ELEM(0,data) /* ret */ \
|
||||
BOOST_PP_SEQ_ELEM(1,data) /* name_from */ ( \
|
||||
BOOST_PP_SEQ_ELEM(3,data) BOOST_PP_SEQ_ELEM(4,data) /* extra arg */\
|
||||
BOOST_PP_COMMA_IF(n) \
|
||||
BOOST_PP_ENUM(n,BOOST_MULTI_INDEX_VARTEMPL_ARG,~)) \
|
||||
{ \
|
||||
return BOOST_PP_SEQ_ELEM(2,data) /* name_to */ ( \
|
||||
BOOST_PP_SEQ_ELEM(4,data) /* extra_arg_name */ \
|
||||
BOOST_PP_COMMA_IF(n) \
|
||||
BOOST_PP_ENUM(n,BOOST_MULTI_INDEX_VARTEMPL_FORWARD_ARG,~) \
|
||||
BOOST_PP_COMMA_IF( \
|
||||
BOOST_PP_SUB(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,n)) \
|
||||
BOOST_PP_ENUM_PARAMS( \
|
||||
BOOST_PP_SUB(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,n), \
|
||||
boost::multi_index::detail::noarg() BOOST_PP_INTERCEPT) \
|
||||
); \
|
||||
}
|
||||
|
||||
#define BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL_EXTRA_ARG( \
|
||||
ret,name_from,name_to,extra_arg_type,extra_arg_name) \
|
||||
BOOST_PP_REPEAT_FROM_TO( \
|
||||
0,BOOST_PP_ADD(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,1), \
|
||||
BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL_EXTRA_ARG_AUX, \
|
||||
(ret)(name_from)(name_to)(extra_arg_type)(extra_arg_name))
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
#define BOOST_MULTI_INDEX_VARTEMPL_TO_PLACEMENT_NEW_AUX(z,n,name) \
|
||||
template< \
|
||||
typename Value \
|
||||
BOOST_PP_COMMA_IF(n) \
|
||||
BOOST_PP_ENUM_PARAMS(n,typename T) \
|
||||
> \
|
||||
Value* name( \
|
||||
Value* x \
|
||||
BOOST_PP_COMMA_IF(n) \
|
||||
BOOST_PP_ENUM(n,BOOST_MULTI_INDEX_VARTEMPL_ARG,~) \
|
||||
BOOST_PP_COMMA_IF( \
|
||||
BOOST_PP_SUB(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,n)) \
|
||||
BOOST_PP_ENUM_PARAMS( \
|
||||
BOOST_PP_SUB(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,n), \
|
||||
BOOST_FWD_REF(noarg) BOOST_PP_INTERCEPT)) \
|
||||
{ \
|
||||
return new(x) Value( \
|
||||
BOOST_PP_ENUM(n,BOOST_MULTI_INDEX_VARTEMPL_FORWARD_ARG,~)); \
|
||||
}
|
||||
|
||||
#define BOOST_MULTI_INDEX_VARTEMPL_TO_PLACEMENT_NEW(name) \
|
||||
BOOST_PP_REPEAT_FROM_TO( \
|
||||
0,BOOST_PP_ADD(BOOST_MULTI_INDEX_LIMIT_VARTEMPL_ARGS,1), \
|
||||
BOOST_MULTI_INDEX_VARTEMPL_TO_PLACEMENT_NEW_AUX, \
|
||||
name)
|
||||
|
||||
BOOST_MULTI_INDEX_VARTEMPL_TO_PLACEMENT_NEW(vartempl_placement_new)
|
||||
|
||||
#undef BOOST_MULTI_INDEX_VARTEMPL_TO_PLACEMENT_NEW_AUX
|
||||
#undef BOOST_MULTI_INDEX_VARTEMPL_TO_PLACEMENT_NEW
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#else
|
||||
|
||||
/* native variadic templates support */
|
||||
|
||||
#include <utility>
|
||||
|
||||
#define BOOST_MULTI_INDEX_TEMPLATE_PARAM_PACK typename... Args
|
||||
#define BOOST_MULTI_INDEX_FUNCTION_PARAM_PACK Args&&... args
|
||||
#define BOOST_MULTI_INDEX_FORWARD_PARAM_PACK std::forward<Args>(args)...
|
||||
#define BOOST_MULTI_INDEX_NULL_PARAM_PACK
|
||||
|
||||
#define BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL( \
|
||||
ret,name_from,name_to) \
|
||||
template<typename... Args> ret name_from(Args&&... args) \
|
||||
{ \
|
||||
return name_to(std::forward<Args>(args)...); \
|
||||
}
|
||||
|
||||
#define BOOST_MULTI_INDEX_OVERLOADS_TO_VARTEMPL_EXTRA_ARG( \
|
||||
ret,name_from,name_to,extra_arg_type,extra_arg_name) \
|
||||
template<typename... Args> ret name_from( \
|
||||
extra_arg_type extra_arg_name,Args&&... args) \
|
||||
{ \
|
||||
return name_to(extra_arg_name,std::forward<Args>(args)...); \
|
||||
}
|
||||
|
||||
namespace boost{
|
||||
|
||||
namespace multi_index{
|
||||
|
||||
namespace detail{
|
||||
|
||||
template<typename Value,typename... Args>
|
||||
Value* vartempl_placement_new(Value*x,Args&&... args)
|
||||
{
|
||||
return new(x) Value(std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
} /* namespace multi_index::detail */
|
||||
|
||||
} /* namespace multi_index */
|
||||
|
||||
} /* namespace boost */
|
||||
|
||||
#endif
|
||||
#endif
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user