mirror of
https://github.com/boostorg/lambda.git
synced 2026-01-21 04:52:25 +00:00
Compare commits
169 Commits
svn-branch
...
master
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
0068b4d90d | ||
|
|
9b378ee3d0 | ||
|
|
eb079473e2 | ||
|
|
8e2446440c | ||
|
|
593ddc7382 | ||
|
|
9fd5cd190e | ||
|
|
cd036b65e2 | ||
|
|
7e792bbbef | ||
|
|
bd56ab5976 | ||
|
|
717daf5483 | ||
|
|
b3d68b5e4e | ||
|
|
f26babea3c | ||
|
|
0d1820513c | ||
|
|
5968889209 | ||
|
|
ea61b3aa85 | ||
|
|
1555e9c7ff | ||
|
|
a3956c27c7 | ||
|
|
ac26514243 | ||
|
|
6b124b66f7 | ||
|
|
568a4d2a63 | ||
|
|
40b6f20419 | ||
|
|
69dd8dd887 | ||
|
|
b17a0c91cd | ||
|
|
3bdaf7096d | ||
|
|
0b84b23cf7 | ||
|
|
0d81c1d25d | ||
|
|
cedabad897 | ||
|
|
24be4d3fe5 | ||
|
|
9709c066fe | ||
|
|
dbca56c00f | ||
|
|
074bc275c8 | ||
|
|
b873d8ef81 | ||
|
|
4bdbb29860 | ||
|
|
e81d400b03 | ||
|
|
5d87ace1e6 | ||
|
|
4007043b54 | ||
|
|
ca87d33f3d | ||
|
|
95e1de198e | ||
|
|
86451f2238 | ||
|
|
a96b87e777 | ||
|
|
bbbe1a9041 | ||
|
|
1a8f8cfead | ||
|
|
7be3075575 | ||
|
|
ddf7dfe25e | ||
|
|
b90488068a | ||
|
|
8de6d9cb9f | ||
|
|
641dd2b0a6 | ||
|
|
d27fc70114 | ||
|
|
1c11cf9570 | ||
|
|
7355f36b9f | ||
|
|
8824e81d52 | ||
|
|
6395013860 | ||
|
|
8c0410fff5 | ||
|
|
b8a2f400ac | ||
|
|
4fc4454f3e | ||
|
|
02999cca47 | ||
|
|
e8eda93ef0 | ||
|
|
9d171774af | ||
|
|
f4b5e00a4f | ||
|
|
42b499ec9b | ||
|
|
61119a8e37 | ||
|
|
4b00716f5f | ||
|
|
4baf512ed2 | ||
|
|
4c0ef8e469 | ||
|
|
18bc9b84cb | ||
|
|
ad5673c9de | ||
|
|
8d9106ab17 | ||
|
|
f12bd0ef93 | ||
|
|
b788075b6d | ||
|
|
5508ede384 | ||
|
|
e4b5434e27 | ||
|
|
4c4387a277 | ||
|
|
0f44d72275 | ||
|
|
723485bfa7 | ||
|
|
f85d2f0025 | ||
|
|
45c391b380 | ||
|
|
69482a3b49 | ||
|
|
0afac59bc1 | ||
|
|
5a6ae7f79d | ||
|
|
9a581dafb7 | ||
|
|
5e574813a2 | ||
|
|
11a6698eec | ||
|
|
5ba2e0aa6a | ||
|
|
59e1516609 | ||
|
|
fba5d5e822 | ||
|
|
635d0fb6ce | ||
|
|
ba8e62af76 | ||
|
|
545b6af540 | ||
|
|
ce6b030b06 | ||
|
|
ecf547cbef | ||
|
|
aef7c9fe51 | ||
|
|
677be04dd7 | ||
|
|
7d1d0d4fdd | ||
|
|
7d21ea7cbb | ||
|
|
0d069c2c0c | ||
|
|
25d6c0e3b1 | ||
|
|
4545234f94 | ||
|
|
657a0b9dd7 | ||
|
|
fab5a8041b | ||
|
|
55cd962166 | ||
|
|
9c376db7e5 | ||
|
|
3caa685662 | ||
|
|
2ed8d7f4df | ||
|
|
2c14c3a13b | ||
|
|
4091f55a4b | ||
|
|
0d0f71272e | ||
|
|
08b3f6336c | ||
|
|
45c6ba535c | ||
|
|
57a605d7cc | ||
|
|
fcfcc42baf | ||
|
|
c516504670 | ||
|
|
c479b3b7b7 | ||
|
|
269ac93b1b | ||
|
|
15d4e6ab79 | ||
|
|
77495bb7e1 | ||
|
|
c183b699bc | ||
|
|
e368877636 | ||
|
|
3d4a3e7050 | ||
|
|
22bc52b7c4 | ||
|
|
8a943f6510 | ||
|
|
c14095472e | ||
|
|
1afc4b6779 | ||
|
|
41eb864595 | ||
|
|
0f60055086 | ||
|
|
d69f83d074 | ||
|
|
9a8e5d7784 | ||
|
|
6985fca6ee | ||
|
|
04ae944c3c | ||
|
|
7648a7adf1 | ||
|
|
0c4e251ebe | ||
|
|
48e6f45d92 | ||
|
|
927a04351e | ||
|
|
0faeb3f19e | ||
|
|
150736273e | ||
|
|
b5b41af8f4 | ||
|
|
1f6ca994e6 | ||
|
|
d5a98758fa | ||
|
|
cd3d5fd03a | ||
|
|
48a89b7705 | ||
|
|
ec350abf06 | ||
|
|
d56abd61ce | ||
|
|
4a254c4161 | ||
|
|
2788ede42a | ||
|
|
1c953ed38c | ||
|
|
b2dc95bb18 | ||
|
|
e67976c740 | ||
|
|
a0cd34c938 | ||
|
|
672c8e10d4 | ||
|
|
797b5756cf | ||
|
|
bd4da55f0f | ||
|
|
87dd3997e7 | ||
|
|
47bf3df0ae | ||
|
|
b112fb9254 | ||
|
|
13ec0c5bbc | ||
|
|
ff0929e6e3 | ||
|
|
29ab5a2814 | ||
|
|
9b925abaff | ||
|
|
a0cfe43611 | ||
|
|
bf50f2fe7f | ||
|
|
fe858cf734 | ||
|
|
85630d55a6 | ||
|
|
2e8c4eb8f3 | ||
|
|
b3120233dc | ||
|
|
24e8602cf1 | ||
|
|
7f77f987c1 | ||
|
|
d854239945 | ||
|
|
4aef261258 | ||
|
|
6b67606f40 | ||
|
|
b0ce56c74f |
643
.github/workflows/ci.yml
vendored
Normal file
643
.github/workflows/ci.yml
vendored
Normal file
@@ -0,0 +1,643 @@
|
||||
name: CI
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
push:
|
||||
branches:
|
||||
- master
|
||||
- develop
|
||||
- feature/**
|
||||
|
||||
env:
|
||||
UBSAN_OPTIONS: print_stacktrace=1
|
||||
|
||||
jobs:
|
||||
posix:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- toolset: gcc-4.8
|
||||
cxxstd: "11"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: g++-4.8
|
||||
- toolset: gcc-5
|
||||
cxxstd: "11,14,1z"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: g++-5
|
||||
- toolset: gcc-6
|
||||
cxxstd: "11,14,1z"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: g++-6
|
||||
- toolset: gcc-7
|
||||
cxxstd: "11,14,17"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: g++-7
|
||||
- toolset: gcc-8
|
||||
cxxstd: "11,14,17,2a"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: g++-8
|
||||
- toolset: gcc-9
|
||||
cxxstd: "11,14,17,2a"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
- toolset: gcc-10
|
||||
cxxstd: "11,14,17,2a"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: g++-10
|
||||
- toolset: gcc-11
|
||||
cxxstd: "11,14,17,2a"
|
||||
os: ubuntu-22.04
|
||||
- toolset: gcc-12
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
os: ubuntu-22.04
|
||||
install: g++-12
|
||||
- toolset: gcc-13
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:24.04
|
||||
os: ubuntu-latest
|
||||
install: g++-13
|
||||
- toolset: gcc-14
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
container: ubuntu:24.04
|
||||
os: ubuntu-latest
|
||||
install: g++-14
|
||||
- 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,1z"
|
||||
os: ubuntu-latest
|
||||
container: ubuntu:18.04
|
||||
install: clang-5.0
|
||||
- toolset: clang
|
||||
compiler: clang++-6.0
|
||||
cxxstd: "11,14,17"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
install: clang-6.0
|
||||
- toolset: clang
|
||||
compiler: clang++-7
|
||||
cxxstd: "11,14,17"
|
||||
container: ubuntu:20.04
|
||||
os: ubuntu-latest
|
||||
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,2a"
|
||||
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
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
os: macos-13
|
||||
- toolset: clang
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
os: macos-14
|
||||
- toolset: clang
|
||||
cxxstd: "11,14,17,20,2b"
|
||||
os: macos-15
|
||||
|
||||
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
|
||||
|
||||
- name: Install nodejs20glibc2.17
|
||||
if: ${{ startsWith( matrix.container, 'ubuntu:1' ) }}
|
||||
run: |
|
||||
curl -LO https://archives.boost.io/misc/node/node-v20.9.0-linux-x64-glibc-217.tar.xz
|
||||
tar -xf node-v20.9.0-linux-x64-glibc-217.tar.xz --strip-components 1 -C /node20217
|
||||
ldd /__e/node20/bin/node
|
||||
|
||||
- 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 --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
|
||||
STDLIB=${{matrix.stdlib}}
|
||||
./b2 -j3 libs/$LIBRARY/test toolset=${{matrix.toolset}} cxxstd=${{matrix.cxxstd}} variant=debug,release ${STDLIB:+stdlib=$STDLIB}
|
||||
|
||||
windows:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- toolset: msvc-14.0
|
||||
cxxstd: "14,latest"
|
||||
addrmd: 32,64
|
||||
os: windows-2019
|
||||
- toolset: msvc-14.2
|
||||
cxxstd: "14,17,20,latest"
|
||||
addrmd: 32,64
|
||||
os: windows-2019
|
||||
- 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-2019
|
||||
|
||||
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 --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
|
||||
|
||||
posix-cmake-subdir:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- os: ubuntu-22.04
|
||||
- os: ubuntu-24.04
|
||||
- os: macos-13
|
||||
- os: macos-14
|
||||
- os: macos-15
|
||||
|
||||
runs-on: ${{matrix.os}}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install packages
|
||||
if: matrix.install
|
||||
run: sudo apt 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
|
||||
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" $LIBRARY
|
||||
|
||||
- name: Use library with add_subdirectory
|
||||
run: |
|
||||
cd ../boost-root/libs/$LIBRARY/test/cmake_subdir_test
|
||||
mkdir __build__ && cd __build__
|
||||
cmake ..
|
||||
cmake --build .
|
||||
ctest --output-on-failure --no-tests=error
|
||||
|
||||
posix-cmake-install:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- os: ubuntu-22.04
|
||||
- os: ubuntu-24.04
|
||||
- os: macos-13
|
||||
- os: macos-14
|
||||
- os: macos-15
|
||||
|
||||
runs-on: ${{matrix.os}}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install packages
|
||||
if: matrix.install
|
||||
run: sudo apt 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
|
||||
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" $LIBRARY
|
||||
|
||||
- name: Configure
|
||||
run: |
|
||||
cd ../boost-root
|
||||
mkdir __build__ && cd __build__
|
||||
cmake -DBOOST_INCLUDE_LIBRARIES=$LIBRARY -DCMAKE_INSTALL_PREFIX=~/.local ..
|
||||
|
||||
- name: Install
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
cmake --build . --target install
|
||||
|
||||
- name: Use the installed library
|
||||
run: |
|
||||
cd ../boost-root/libs/$LIBRARY/test/cmake_install_test && mkdir __build__ && cd __build__
|
||||
cmake -DCMAKE_INSTALL_PREFIX=~/.local ..
|
||||
cmake --build .
|
||||
ctest --output-on-failure --no-tests=error
|
||||
|
||||
posix-cmake-test:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- os: ubuntu-22.04
|
||||
- os: ubuntu-24.04
|
||||
- os: macos-13
|
||||
- os: macos-14
|
||||
- os: macos-15
|
||||
|
||||
runs-on: ${{matrix.os}}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Install packages
|
||||
if: matrix.install
|
||||
run: sudo apt 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
|
||||
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" $LIBRARY
|
||||
|
||||
- name: Configure
|
||||
run: |
|
||||
cd ../boost-root
|
||||
mkdir __build__ && cd __build__
|
||||
cmake -DBOOST_INCLUDE_LIBRARIES=$LIBRARY -DBUILD_TESTING=ON ..
|
||||
|
||||
- name: Build tests
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
cmake --build . --target tests
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
ctest --output-on-failure --no-tests=error
|
||||
|
||||
windows-cmake-subdir:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- os: windows-2019
|
||||
- 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 --git_args "--jobs 3" %LIBRARY%
|
||||
|
||||
- name: Use library with add_subdirectory (Debug)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/libs/%LIBRARY%/test/cmake_subdir_test
|
||||
mkdir __build__ && cd __build__
|
||||
cmake ..
|
||||
cmake --build . --config Debug
|
||||
ctest --output-on-failure --no-tests=error -C Debug
|
||||
|
||||
- name: Use library with add_subdirectory (Release)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/libs/%LIBRARY%/test/cmake_subdir_test/__build__
|
||||
cmake --build . --config Release
|
||||
ctest --output-on-failure --no-tests=error -C Release
|
||||
|
||||
windows-cmake-install:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- os: windows-2019
|
||||
- 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 --git_args "--jobs 3" %LIBRARY%
|
||||
|
||||
- name: Configure
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root
|
||||
mkdir __build__ && cd __build__
|
||||
cmake -DBOOST_INCLUDE_LIBRARIES=%LIBRARY% -DCMAKE_INSTALL_PREFIX=C:/cmake-prefix ..
|
||||
|
||||
- name: Install (Debug)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
cmake --build . --target install --config Debug
|
||||
|
||||
- name: Install (Release)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
cmake --build . --target install --config Release
|
||||
|
||||
- name: Use the installed library (Debug)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/libs/%LIBRARY%/test/cmake_install_test && mkdir __build__ && cd __build__
|
||||
cmake -DCMAKE_INSTALL_PREFIX=C:/cmake-prefix ..
|
||||
cmake --build . --config Debug
|
||||
ctest --output-on-failure --no-tests=error -C Debug
|
||||
|
||||
- name: Use the installed library (Release)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/libs/%LIBRARY%/test/cmake_install_test/__build__
|
||||
cmake --build . --config Release
|
||||
ctest --output-on-failure --no-tests=error -C Release
|
||||
|
||||
windows-cmake-test:
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
include:
|
||||
- os: windows-2019
|
||||
- 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 --git_args "--jobs 3" %LIBRARY%
|
||||
|
||||
- name: Configure
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root
|
||||
mkdir __build__ && cd __build__
|
||||
cmake -DBOOST_INCLUDE_LIBRARIES=%LIBRARY% -DBUILD_TESTING=ON ..
|
||||
|
||||
- name: Build tests (Debug)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
cmake --build . --target tests --config Debug
|
||||
|
||||
- name: Run tests (Debug)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
ctest --output-on-failure --no-tests=error -C Debug
|
||||
|
||||
- name: Build tests (Release)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
cmake --build . --target tests --config Release
|
||||
|
||||
- name: Run tests (Release)
|
||||
shell: cmd
|
||||
run: |
|
||||
cd ../boost-root/__build__
|
||||
ctest --output-on-failure --no-tests=error -C Release
|
||||
163
.travis.yml
Normal file
163
.travis.yml
Normal file
@@ -0,0 +1,163 @@
|
||||
# Copyright 2016 Edward Diener
|
||||
# Copyright 2016, 2017, 2021 Peter Dimov
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at http://boost.org/LICENSE_1_0.txt)
|
||||
|
||||
language: cpp
|
||||
|
||||
dist: xenial
|
||||
|
||||
branches:
|
||||
only:
|
||||
- master
|
||||
- develop
|
||||
- /feature\/.*/
|
||||
|
||||
env:
|
||||
matrix:
|
||||
- BOGUS_JOB=true
|
||||
|
||||
matrix:
|
||||
|
||||
exclude:
|
||||
- env: BOGUS_JOB=true
|
||||
|
||||
include:
|
||||
- os: linux
|
||||
compiler: g++-4.4
|
||||
env: TOOLSET=gcc CXXSTD=98
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- g++-4.4
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
|
||||
- os: linux
|
||||
compiler: g++-4.6
|
||||
env: TOOLSET=gcc CXXSTD=03,0x
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- g++-4.6
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
|
||||
- os: linux
|
||||
compiler: g++-4.8
|
||||
env: TOOLSET=gcc CXXSTD=03,11
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- g++-4.8
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
|
||||
- os: linux
|
||||
compiler: g++-5
|
||||
env: TOOLSET=gcc CXXSTD=03,11,14
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- g++-5
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
|
||||
- os: linux
|
||||
compiler: g++-7
|
||||
env: TOOLSET=gcc CXXSTD=03,11,14,17
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- g++-7
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
|
||||
- os: linux
|
||||
compiler: g++-9
|
||||
env: TOOLSET=gcc CXXSTD=03,11,14,17
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- g++-9
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
|
||||
- os: linux
|
||||
dist: bionic
|
||||
compiler: g++-10
|
||||
env: TOOLSET=gcc CXXSTD=03,11,14,17,2a
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- g++-10
|
||||
sources:
|
||||
- sourceline: "ppa:ubuntu-toolchain-r/test"
|
||||
|
||||
- os: linux
|
||||
dist: bionic
|
||||
compiler: g++-11
|
||||
env: UBSAN=1 TOOLSET=gcc CXXSTD=03,11,14,17,20 UBSAN_OPTIONS=print_stacktrace=1 LINKFLAGS=-fuse-ld=gold
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- g++-11
|
||||
sources:
|
||||
- sourceline: "ppa:ubuntu-toolchain-r/test"
|
||||
|
||||
- os: linux
|
||||
compiler: clang++-11
|
||||
env: TOOLSET=clang CXXSTD=03,11,14,17,20
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- clang-11
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- sourceline: 'deb https://apt.llvm.org/xenial/ llvm-toolchain-xenial-11 main'
|
||||
key_url: 'https://apt.llvm.org/llvm-snapshot.gpg.key'
|
||||
|
||||
- os: linux
|
||||
compiler: clang++-12
|
||||
env: UBSAN=1 TOOLSET=clang CXXSTD=03,11,14,17,20 UBSAN_OPTIONS=print_stacktrace=1
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- clang-12
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- sourceline: 'deb https://apt.llvm.org/xenial/ llvm-toolchain-xenial-12 main'
|
||||
key_url: 'https://apt.llvm.org/llvm-snapshot.gpg.key'
|
||||
|
||||
- os: linux
|
||||
dist: bionic
|
||||
compiler: clang++-libc++
|
||||
env: TOOLSET=clang CXXSTD=03,11,14,17,2a
|
||||
addons:
|
||||
apt:
|
||||
packages:
|
||||
- libc++-dev
|
||||
|
||||
- os: osx
|
||||
compiler: clang++
|
||||
env: UBSAN=1 TOOLSET=clang CXXSTD=03,11,14,1z UBSAN_OPTIONS=print_stacktrace=1
|
||||
|
||||
install:
|
||||
- BOOST_BRANCH=develop && [ "$TRAVIS_BRANCH" == "master" ] && BOOST_BRANCH=master || true
|
||||
- cd ..
|
||||
- git clone -b $BOOST_BRANCH https://github.com/boostorg/boost.git boost-root
|
||||
- cd boost-root
|
||||
- git submodule update --init tools/boostdep
|
||||
- cp -r $TRAVIS_BUILD_DIR/* libs/lambda
|
||||
- python tools/boostdep/depinst/depinst.py lambda
|
||||
- ./bootstrap.sh
|
||||
- ./b2 headers
|
||||
|
||||
script:
|
||||
- |-
|
||||
echo "using $TOOLSET : : $TRAVIS_COMPILER ;" > ~/user-config.jam
|
||||
- ./b2 -j3 libs/lambda/test toolset=$TOOLSET cxxstd=$CXXSTD variant=debug,release ${UBSAN:+cxxflags=-fsanitize=undefined cxxflags=-fno-sanitize-recover=undefined linkflags=-fsanitize=undefined define=UBSAN=1 debug-symbols=on} ${LINKFLAGS:+linkflags=$LINKFLAGS}
|
||||
|
||||
notifications:
|
||||
email:
|
||||
on_success: always
|
||||
34
CMakeLists.txt
Normal file
34
CMakeLists.txt
Normal file
@@ -0,0 +1,34 @@
|
||||
# Generated by `boostdep --cmake lambda`
|
||||
# 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.5...3.16)
|
||||
|
||||
project(boost_lambda VERSION "${BOOST_SUPERPROJECT_VERSION}" LANGUAGES CXX)
|
||||
|
||||
add_library(boost_lambda INTERFACE)
|
||||
add_library(Boost::lambda ALIAS boost_lambda)
|
||||
|
||||
target_include_directories(boost_lambda INTERFACE include)
|
||||
|
||||
target_link_libraries(boost_lambda
|
||||
INTERFACE
|
||||
Boost::bind
|
||||
Boost::config
|
||||
Boost::core
|
||||
Boost::detail
|
||||
Boost::iterator
|
||||
Boost::mpl
|
||||
Boost::preprocessor
|
||||
Boost::tuple
|
||||
Boost::type_traits
|
||||
Boost::utility
|
||||
)
|
||||
|
||||
if(BUILD_TESTING AND EXISTS "${CMAKE_CURRENT_SOURCE_DIR}/test/CMakeLists.txt")
|
||||
|
||||
add_subdirectory(test)
|
||||
|
||||
endif()
|
||||
|
||||
46
appveyor.yml
Normal file
46
appveyor.yml
Normal file
@@ -0,0 +1,46 @@
|
||||
# Copyright 2016-2021 Peter Dimov
|
||||
# Distributed under the Boost Software License, Version 1.0.
|
||||
# (See accompanying file LICENSE_1_0.txt or copy at http://boost.org/LICENSE_1_0.txt)
|
||||
|
||||
version: 1.0.{build}-{branch}
|
||||
|
||||
shallow_clone: true
|
||||
|
||||
branches:
|
||||
only:
|
||||
- master
|
||||
- develop
|
||||
- /feature\/.*/
|
||||
|
||||
environment:
|
||||
matrix:
|
||||
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015
|
||||
TOOLSET: msvc-14.0
|
||||
ADDRMD: 32,64
|
||||
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017
|
||||
TOOLSET: msvc-14.1
|
||||
CXXSTD: 14,17,latest
|
||||
ADDRMD: 32,64
|
||||
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2019
|
||||
TOOLSET: clang-win
|
||||
CXXSTD: 14,17,latest
|
||||
ADDRMD: 32,64
|
||||
|
||||
install:
|
||||
- set BOOST_BRANCH=develop
|
||||
- if "%APPVEYOR_REPO_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 %APPVEYOR_BUILD_FOLDER% libs\lambda\
|
||||
- python tools/boostdep/depinst/depinst.py lambda
|
||||
- cmd /c bootstrap
|
||||
- b2 -d0 headers
|
||||
|
||||
build: off
|
||||
|
||||
test_script:
|
||||
- if not "%CXXSTD%" == "" set CXXSTD=cxxstd=%CXXSTD%
|
||||
- if not "%ADDRMD%" == "" set ADDRMD=address-model=%ADDRMD%
|
||||
- b2 -j3 libs/lambda/test toolset=%TOOLSET% %CXXSTD% %ADDRMD% variant=debug,release embed-manifest-via=linker
|
||||
30
build.jam
Normal file
30
build.jam
Normal file
@@ -0,0 +1,30 @@
|
||||
# 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/bind//boost_bind
|
||||
/boost/config//boost_config
|
||||
/boost/core//boost_core
|
||||
/boost/detail//boost_detail
|
||||
/boost/iterator//boost_iterator
|
||||
/boost/mpl//boost_mpl
|
||||
/boost/preprocessor//boost_preprocessor
|
||||
/boost/tuple//boost_tuple
|
||||
/boost/type_traits//boost_type_traits
|
||||
/boost/utility//boost_utility ;
|
||||
|
||||
project /boost/lambda
|
||||
;
|
||||
|
||||
explicit
|
||||
[ alias boost_lambda : : :
|
||||
: <include>include <library>$(boost_dependencies) ]
|
||||
[ alias all : boost_lambda test ]
|
||||
;
|
||||
|
||||
call-if : boost-library lambda
|
||||
;
|
||||
@@ -1,5 +1,21 @@
|
||||
project boost/doc ;
|
||||
project lambda/doc ;
|
||||
import boostbook : boostbook ;
|
||||
|
||||
boostbook lambda-doc : lambda.xml ;
|
||||
# Are these really the correct images??
|
||||
path-constant images : ../../spirit/phoenix/doc/html ;
|
||||
|
||||
boostbook lambda-doc : lambda.xml
|
||||
:
|
||||
<xsl:param>boost.root=../../../..
|
||||
<format>pdf:<xsl:param>img.src.path=$(images)/
|
||||
;
|
||||
|
||||
###############################################################################
|
||||
alias boostdoc
|
||||
: lambda.xml
|
||||
:
|
||||
:
|
||||
: ;
|
||||
explicit boostdoc ;
|
||||
alias boostrelease ;
|
||||
explicit boostrelease ;
|
||||
|
||||
8
doc/detail/lambda_doc.xml
Executable file → Normal file
8
doc/detail/lambda_doc.xml
Executable file → Normal file
@@ -163,8 +163,8 @@ The STL contains predefined function objects for some common cases (such as <lit
|
||||
As an example, one possible implementation for the standard <literal>plus</literal> template is:
|
||||
|
||||
<programlisting>
|
||||
<![CDATA[template <class T> : public binary_function<T, T, T>
|
||||
struct plus {
|
||||
<![CDATA[template <class T>
|
||||
struct plus : public binary_function<T, T, T> {
|
||||
T operator()(const T& i, const T& j) const {
|
||||
return i + j;
|
||||
}
|
||||
@@ -3281,7 +3281,7 @@ was dropped.
|
||||
<abbrev>SGI02</abbrev>
|
||||
<title>The SGI Standard Template Library</title>
|
||||
<pubdate>2002</pubdate>
|
||||
<bibliomisc><ulink url="http://www.sgi.com/tech/stl/">www.sgi.com/tech/stl/</ulink></bibliomisc>
|
||||
<bibliomisc><ulink url="https://www.boost.org/sgi/stl/">www.boost.org/sgi/stl/</ulink></bibliomisc>
|
||||
|
||||
</biblioentry>
|
||||
|
||||
@@ -3435,7 +3435,7 @@ was dropped.
|
||||
<firstname>Brian</firstname>
|
||||
<surname>McNamara</surname>
|
||||
</author>
|
||||
<bibliomisc><ulink url="http://www.cc.gatech.edu/~yannis/fc++/">www.cc.gatech.edu/~yannis/fc++/</ulink>
|
||||
<bibliomisc><ulink url="http://yanniss.github.io/fc++/">yanniss.github.io/fc++/ </ulink>
|
||||
</bibliomisc>
|
||||
<pubdate>2002</pubdate>
|
||||
</biblioentry>
|
||||
|
||||
@@ -3,6 +3,10 @@
|
||||
<meta http-equiv="refresh" content="0; URL=../../../doc/html/lambda.html">
|
||||
</head>
|
||||
<body>
|
||||
Automatic redirection failed, please go to <a href="../../../doc/html/lambda.html">www.boost.org/doc/html/lambda.html</a>
|
||||
Automatic redirection failed, please go to <a href="../../../doc/html/lambda.html">www.boost.org/doc/html/lambda.html</a> <hr>
|
||||
<p>© Copyright Beman Dawes, 2001</p>
|
||||
<p>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">www.boost.org/LICENSE_1_0.txt</a>)</p>
|
||||
</body>
|
||||
</html>
|
||||
</html>
|
||||
|
||||
@@ -44,7 +44,7 @@
|
||||
<para>
|
||||
|
||||
The Boost Lambda Library (BLL in the sequel) is a C++ template
|
||||
library, which implements form of <emphasis>lambda abstractions</emphasis> for C++.
|
||||
library, which implements a form of <emphasis>lambda abstractions</emphasis> for C++.
|
||||
The term originates from functional programming and lambda calculus, where a lambda abstraction defines an unnamed function.
|
||||
The primary motivation for the BLL is to provide flexible and
|
||||
convenient means to define unnamed function objects for STL algorithms.
|
||||
@@ -165,8 +165,8 @@ The STL contains predefined function objects for some common cases (such as <lit
|
||||
As an example, one possible implementation for the standard <literal>plus</literal> template is:
|
||||
|
||||
<programlisting>
|
||||
<![CDATA[template <class T> : public binary_function<T, T, T>
|
||||
struct plus {
|
||||
<![CDATA[template <class T>
|
||||
struct plus : public binary_function<T, T, T> {
|
||||
T operator()(const T& i, const T& j) const {
|
||||
return i + j;
|
||||
}
|
||||
@@ -1908,7 +1908,7 @@ For example:
|
||||
int foo(int); int bar(int);
|
||||
...
|
||||
int i;
|
||||
bind(foo, bind(bar, _1)(i);
|
||||
bind(foo, bind(bar, _1))(i);
|
||||
</programlisting>
|
||||
|
||||
The last line makes the call <literal>foo(bar(i));</literal>
|
||||
@@ -2640,6 +2640,7 @@ which require that the argument types are references.
|
||||
<row><entry><literal><![CDATA[&]]></literal></entry><entry><literal><![CDATA[other_action<address_of_action>]]></literal></entry></row>
|
||||
<row><entry><literal><![CDATA[*]]></literal></entry><entry><literal><![CDATA[other_action<contents_of_action>]]></literal></entry></row>
|
||||
<row><entry><literal><![CDATA[,]]></literal></entry><entry><literal><![CDATA[other_action<comma_action>]]></literal></entry></row>
|
||||
<row><entry><literal><![CDATA[->*]]></literal></entry><entry><literal><![CDATA[other_action<member_pointer_action>]]></literal></entry></row>
|
||||
|
||||
</tbody>
|
||||
</tgroup>
|
||||
@@ -3190,7 +3191,7 @@ to extend the library with new features.
|
||||
|
||||
|
||||
|
||||
<appendix>
|
||||
<section>
|
||||
<title>Rationale for some of the design decisions</title>
|
||||
|
||||
<section id="lambda.why_weak_arity">
|
||||
@@ -3255,7 +3256,7 @@ was dropped.
|
||||
|
||||
</section>
|
||||
|
||||
</appendix>
|
||||
</section>
|
||||
|
||||
|
||||
|
||||
@@ -3285,7 +3286,7 @@ was dropped.
|
||||
<abbrev>SGI02</abbrev>
|
||||
<title>The SGI Standard Template Library</title>
|
||||
<pubdate>2002</pubdate>
|
||||
<bibliomisc><ulink url="http://www.sgi.com/tech/stl/">www.sgi.com/tech/stl/</ulink></bibliomisc>
|
||||
<bibliomisc><ulink url="https://www.boost.org/sgi/stl/">www.boost.org/sgi/stl/</ulink></bibliomisc>
|
||||
|
||||
</biblioentry>
|
||||
|
||||
@@ -3439,7 +3440,7 @@ was dropped.
|
||||
<firstname>Brian</firstname>
|
||||
<surname>McNamara</surname>
|
||||
</author>
|
||||
<bibliomisc><ulink url="http://www.cc.gatech.edu/~yannis/fc++/">www.cc.gatech.edu/~yannis/fc++/</ulink>
|
||||
<bibliomisc><ulink url="http://yanniss.github.io/fc++/">yanniss.github.io/fc++/ </ulink>
|
||||
</bibliomisc>
|
||||
<pubdate>2002</pubdate>
|
||||
</biblioentry>
|
||||
|
||||
1380
include/boost/lambda/algorithm.hpp
Normal file
1380
include/boost/lambda/algorithm.hpp
Normal file
File diff suppressed because it is too large
Load Diff
24
include/boost/lambda/bind.hpp
Normal file
24
include/boost/lambda/bind.hpp
Normal file
@@ -0,0 +1,24 @@
|
||||
// -- bind.hpp -- Boost Lambda Library --------------------------------------
|
||||
|
||||
// Copyright (C) 1999-2001 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Gary Powell (gwpowell@hotmail.com)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see http://www.boost.org
|
||||
|
||||
#ifndef BOOST_LAMBDA_BIND_HPP
|
||||
#define BOOST_LAMBDA_BIND_HPP
|
||||
|
||||
#include "boost/lambda/core.hpp"
|
||||
|
||||
// Required for std::is_assignable to work on the result of bind()
|
||||
#include "boost/lambda/detail/operator_actions.hpp"
|
||||
#include "boost/lambda/detail/operator_lambda_func_base.hpp"
|
||||
#include "boost/lambda/detail/operator_return_type_traits.hpp"
|
||||
|
||||
#include "boost/lambda/detail/bind_functions.hpp"
|
||||
|
||||
#endif
|
||||
226
include/boost/lambda/casts.hpp
Normal file
226
include/boost/lambda/casts.hpp
Normal file
@@ -0,0 +1,226 @@
|
||||
// - casts.hpp -- BLambda Library -------------
|
||||
//
|
||||
// Copyright (C) 2000 Gary Powell (powellg@amazon.com)
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see http://www.boost.org
|
||||
|
||||
// -----------------------------------------------
|
||||
|
||||
#if !defined(BOOST_LAMBDA_CASTS_HPP)
|
||||
#define BOOST_LAMBDA_CASTS_HPP
|
||||
|
||||
#include "boost/lambda/detail/suppress_unused.hpp"
|
||||
#include "boost/lambda/core.hpp"
|
||||
|
||||
#include <typeinfo>
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
template<class Act, class Args>
|
||||
struct return_type_N;
|
||||
|
||||
template<class T> class cast_action;
|
||||
|
||||
template<class T> class static_cast_action;
|
||||
template<class T> class dynamic_cast_action;
|
||||
template<class T> class const_cast_action;
|
||||
template<class T> class reinterpret_cast_action;
|
||||
|
||||
class typeid_action;
|
||||
class sizeof_action;
|
||||
|
||||
// Cast actions
|
||||
|
||||
template<class T> class cast_action<static_cast_action<T> >
|
||||
{
|
||||
public:
|
||||
template<class RET, class Arg1>
|
||||
static RET apply(Arg1 &a1) {
|
||||
return static_cast<RET>(a1);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class cast_action<dynamic_cast_action<T> > {
|
||||
public:
|
||||
template<class RET, class Arg1>
|
||||
static RET apply(Arg1 &a1) {
|
||||
return dynamic_cast<RET>(a1);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class cast_action<const_cast_action<T> > {
|
||||
public:
|
||||
template<class RET, class Arg1>
|
||||
static RET apply(Arg1 &a1) {
|
||||
return const_cast<RET>(a1);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class cast_action<reinterpret_cast_action<T> > {
|
||||
public:
|
||||
template<class RET, class Arg1>
|
||||
static RET apply(Arg1 &a1) {
|
||||
return reinterpret_cast<RET>(a1);
|
||||
}
|
||||
};
|
||||
|
||||
// typeid action
|
||||
class typeid_action {
|
||||
public:
|
||||
template<class RET, class Arg1>
|
||||
static RET apply(Arg1 &a1) {
|
||||
detail::suppress_unused_variable_warnings(a1);
|
||||
return typeid(a1);
|
||||
}
|
||||
};
|
||||
|
||||
// sizeof action
|
||||
class sizeof_action
|
||||
{
|
||||
public:
|
||||
template<class RET, class Arg1>
|
||||
static RET apply(Arg1 &a1) {
|
||||
return sizeof(a1);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// return types of casting lambda_functors (all "T" type.)
|
||||
|
||||
template<template <class> class cast_type, class T, class A>
|
||||
struct return_type_N<cast_action< cast_type<T> >, A> {
|
||||
typedef T type;
|
||||
};
|
||||
|
||||
// return type of typeid_action
|
||||
template<class A>
|
||||
struct return_type_N<typeid_action, A> {
|
||||
typedef std::type_info const & type;
|
||||
};
|
||||
|
||||
// return type of sizeof_action
|
||||
|
||||
template<class A>
|
||||
struct return_type_N<sizeof_action, A> {
|
||||
typedef std::size_t type;
|
||||
};
|
||||
|
||||
|
||||
// the four cast & typeid overloads.
|
||||
// casts can take ordinary variables (not just lambda functors)
|
||||
|
||||
// static_cast
|
||||
template <class T, class Arg1>
|
||||
inline const lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<1, cast_action<static_cast_action<T> > >,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
>
|
||||
ll_static_cast(const Arg1& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<1, cast_action<static_cast_action<T> > >,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
( tuple<typename const_copy_argument <const Arg1>::type>(a1));
|
||||
}
|
||||
|
||||
// dynamic_cast
|
||||
template <class T, class Arg1>
|
||||
inline const lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<1, cast_action<dynamic_cast_action<T> > >,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
>
|
||||
ll_dynamic_cast(const Arg1& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<1, cast_action<dynamic_cast_action<T> > >,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
( tuple<typename const_copy_argument <const Arg1>::type>(a1));
|
||||
}
|
||||
|
||||
// const_cast
|
||||
template <class T, class Arg1>
|
||||
inline const lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<1, cast_action<const_cast_action<T> > >,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
>
|
||||
ll_const_cast(const Arg1& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<1, cast_action<const_cast_action<T> > >,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
( tuple<typename const_copy_argument <const Arg1>::type>(a1));
|
||||
}
|
||||
|
||||
// reinterpret_cast
|
||||
template <class T, class Arg1>
|
||||
inline const lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<1, cast_action<reinterpret_cast_action<T> > >,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
>
|
||||
ll_reinterpret_cast(const Arg1& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<1, cast_action<reinterpret_cast_action<T> > >,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
( tuple<typename const_copy_argument <const Arg1>::type>(a1));
|
||||
}
|
||||
|
||||
// typeid
|
||||
// can be applied to a normal variable as well (can refer to a polymorphic
|
||||
// class object)
|
||||
template <class Arg1>
|
||||
inline const lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<1, typeid_action>,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
>
|
||||
ll_typeid(const Arg1& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<1, typeid_action>,
|
||||
tuple<typename const_copy_argument <const Arg1>::type>
|
||||
>
|
||||
( tuple<typename const_copy_argument <const Arg1>::type>(a1));
|
||||
}
|
||||
|
||||
// sizeof(expression)
|
||||
// Always takes a lambda expression (if not, built in sizeof will do)
|
||||
template <class Arg1>
|
||||
inline const lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<1, sizeof_action>,
|
||||
tuple<lambda_functor<Arg1> >
|
||||
>
|
||||
>
|
||||
ll_sizeof(const lambda_functor<Arg1>& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<1, sizeof_action>,
|
||||
tuple<lambda_functor<Arg1> >
|
||||
>
|
||||
( tuple<lambda_functor<Arg1> >(a1));
|
||||
}
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
274
include/boost/lambda/closures.hpp
Normal file
274
include/boost/lambda/closures.hpp
Normal file
@@ -0,0 +1,274 @@
|
||||
/*=============================================================================
|
||||
Adaptable closures
|
||||
|
||||
Phoenix V0.9
|
||||
Copyright (c) 2001-2002 Joel de Guzman
|
||||
|
||||
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)
|
||||
|
||||
URL: http://spirit.sourceforge.net/
|
||||
|
||||
==============================================================================*/
|
||||
#ifndef BOOST_LAMBDA_CLOSURES_HPP
|
||||
#define BOOST_LAMBDA_CLOSURES_HPP
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
#include "boost/lambda/core.hpp"
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Adaptable closures
|
||||
//
|
||||
// The framework will not be complete without some form of closures
|
||||
// support. Closures encapsulate a stack frame where local
|
||||
// variables are created upon entering a function and destructed
|
||||
// upon exiting. Closures provide an environment for local
|
||||
// variables to reside. Closures can hold heterogeneous types.
|
||||
//
|
||||
// Phoenix closures are true hardware stack based closures. At the
|
||||
// very least, closures enable true reentrancy in lambda functions.
|
||||
// A closure provides access to a function stack frame where local
|
||||
// variables reside. Modeled after Pascal nested stack frames,
|
||||
// closures can be nested just like nested functions where code in
|
||||
// inner closures may access local variables from in-scope outer
|
||||
// closures (accessing inner scopes from outer scopes is an error
|
||||
// and will cause a run-time assertion failure).
|
||||
//
|
||||
// There are three (3) interacting classes:
|
||||
//
|
||||
// 1) closure:
|
||||
//
|
||||
// At the point of declaration, a closure does not yet create a
|
||||
// stack frame nor instantiate any variables. A closure declaration
|
||||
// declares the types and names[note] of the local variables. The
|
||||
// closure class is meant to be subclassed. It is the
|
||||
// responsibility of a closure subclass to supply the names for
|
||||
// each of the local variable in the closure. Example:
|
||||
//
|
||||
// struct my_closure : closure<int, string, double> {
|
||||
//
|
||||
// member1 num; // names the 1st (int) local variable
|
||||
// member2 message; // names the 2nd (string) local variable
|
||||
// member3 real; // names the 3rd (double) local variable
|
||||
// };
|
||||
//
|
||||
// my_closure clos;
|
||||
//
|
||||
// Now that we have a closure 'clos', its local variables can be
|
||||
// accessed lazily using the dot notation. Each qualified local
|
||||
// variable can be used just like any primitive actor (see
|
||||
// primitives.hpp). Examples:
|
||||
//
|
||||
// clos.num = 30
|
||||
// clos.message = arg1
|
||||
// clos.real = clos.num * 1e6
|
||||
//
|
||||
// The examples above are lazily evaluated. As usual, these
|
||||
// expressions return composite actors that will be evaluated
|
||||
// through a second function call invocation (see operators.hpp).
|
||||
// Each of the members (clos.xxx) is an actor. As such, applying
|
||||
// the operator() will reveal its identity:
|
||||
//
|
||||
// clos.num() // will return the current value of clos.num
|
||||
//
|
||||
// *** [note] Acknowledgement: Juan Carlos Arevalo-Baeza (JCAB)
|
||||
// introduced and initilally implemented the closure member names
|
||||
// that uses the dot notation.
|
||||
//
|
||||
// 2) closure_member
|
||||
//
|
||||
// The named local variables of closure 'clos' above are actually
|
||||
// closure members. The closure_member class is an actor and
|
||||
// conforms to its conceptual interface. member1..memberN are
|
||||
// predefined typedefs that correspond to each of the listed types
|
||||
// in the closure template parameters.
|
||||
//
|
||||
// 3) closure_frame
|
||||
//
|
||||
// When a closure member is finally evaluated, it should refer to
|
||||
// an actual instance of the variable in the hardware stack.
|
||||
// Without doing so, the process is not complete and the evaluated
|
||||
// member will result to an assertion failure. Remember that the
|
||||
// closure is just a declaration. The local variables that a
|
||||
// closure refers to must still be instantiated.
|
||||
//
|
||||
// The closure_frame class does the actual instantiation of the
|
||||
// local variables and links these variables with the closure and
|
||||
// all its members. There can be multiple instances of
|
||||
// closure_frames typically situated in the stack inside a
|
||||
// function. Each closure_frame instance initiates a stack frame
|
||||
// with a new set of closure local variables. Example:
|
||||
//
|
||||
// void foo()
|
||||
// {
|
||||
// closure_frame<my_closure> frame(clos);
|
||||
// /* do something */
|
||||
// }
|
||||
//
|
||||
// where 'clos' is an instance of our closure 'my_closure' above.
|
||||
// Take note that the usage above precludes locally declared
|
||||
// classes. If my_closure is a locally declared type, we can still
|
||||
// use its self_type as a paramater to closure_frame:
|
||||
//
|
||||
// closure_frame<my_closure::self_type> frame(clos);
|
||||
//
|
||||
// Upon instantiation, the closure_frame links the local variables
|
||||
// to the closure. The previous link to another closure_frame
|
||||
// instance created before is saved. Upon destruction, the
|
||||
// closure_frame unlinks itself from the closure and relinks the
|
||||
// preceding closure_frame prior to this instance.
|
||||
//
|
||||
// The local variables in the closure 'clos' above is default
|
||||
// constructed in the stack inside function 'foo'. Once 'foo' is
|
||||
// exited, all of these local variables are destructed. In some
|
||||
// cases, default construction is not desirable and we need to
|
||||
// initialize the local closure variables with some values. This
|
||||
// can be done by passing in the initializers in a compatible
|
||||
// tuple. A compatible tuple is one with the same number of
|
||||
// elements as the destination and where each element from the
|
||||
// destination can be constructed from each corresponding element
|
||||
// in the source. Example:
|
||||
//
|
||||
// tuple<int, char const*, int> init(123, "Hello", 1000);
|
||||
// closure_frame<my_closure> frame(clos, init);
|
||||
//
|
||||
// Here now, our closure_frame's variables are initialized with
|
||||
// int: 123, char const*: "Hello" and int: 1000.
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// closure_frame class
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename ClosureT>
|
||||
class closure_frame : public ClosureT::tuple_t {
|
||||
|
||||
public:
|
||||
|
||||
closure_frame(ClosureT& clos)
|
||||
: ClosureT::tuple_t(), save(clos.frame), frame(clos.frame)
|
||||
{ clos.frame = this; }
|
||||
|
||||
template <typename TupleT>
|
||||
closure_frame(ClosureT& clos, TupleT const& init)
|
||||
: ClosureT::tuple_t(init), save(clos.frame), frame(clos.frame)
|
||||
{ clos.frame = this; }
|
||||
|
||||
~closure_frame()
|
||||
{ frame = save; }
|
||||
|
||||
private:
|
||||
|
||||
closure_frame(closure_frame const&); // no copy
|
||||
closure_frame& operator=(closure_frame const&); // no assign
|
||||
|
||||
closure_frame* save;
|
||||
closure_frame*& frame;
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// closure_member class
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <int N, typename ClosureT>
|
||||
class closure_member {
|
||||
|
||||
public:
|
||||
|
||||
typedef typename ClosureT::tuple_t tuple_t;
|
||||
|
||||
closure_member()
|
||||
: frame(ClosureT::closure_frame_ref()) {}
|
||||
|
||||
template <typename TupleT>
|
||||
struct sig {
|
||||
|
||||
typedef typename detail::tuple_element_as_reference<
|
||||
N, typename ClosureT::tuple_t
|
||||
>::type type;
|
||||
};
|
||||
|
||||
template <class Ret, class A, class B, class C>
|
||||
// typename detail::tuple_element_as_reference
|
||||
// <N, typename ClosureT::tuple_t>::type
|
||||
Ret
|
||||
call(A&, B&, C&) const
|
||||
{
|
||||
assert(frame);
|
||||
return boost::tuples::get<N>(*frame);
|
||||
}
|
||||
|
||||
|
||||
private:
|
||||
|
||||
typename ClosureT::closure_frame_t*& frame;
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// closure class
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <
|
||||
typename T0 = null_type,
|
||||
typename T1 = null_type,
|
||||
typename T2 = null_type,
|
||||
typename T3 = null_type,
|
||||
typename T4 = null_type
|
||||
>
|
||||
class closure {
|
||||
|
||||
public:
|
||||
|
||||
typedef tuple<T0, T1, T2, T3, T4> tuple_t;
|
||||
typedef closure<T0, T1, T2, T3, T4> self_t;
|
||||
typedef closure_frame<self_t> closure_frame_t;
|
||||
|
||||
closure()
|
||||
: frame(0) { closure_frame_ref(&frame); }
|
||||
closure_frame_t& context() { assert(frame); return frame; }
|
||||
closure_frame_t const& context() const { assert(frame); return frame; }
|
||||
|
||||
typedef lambda_functor<closure_member<0, self_t> > member1;
|
||||
typedef lambda_functor<closure_member<1, self_t> > member2;
|
||||
typedef lambda_functor<closure_member<2, self_t> > member3;
|
||||
typedef lambda_functor<closure_member<3, self_t> > member4;
|
||||
typedef lambda_functor<closure_member<4, self_t> > member5;
|
||||
|
||||
private:
|
||||
|
||||
closure(closure const&); // no copy
|
||||
closure& operator=(closure const&); // no assign
|
||||
|
||||
template <int N, typename ClosureT>
|
||||
friend class closure_member;
|
||||
|
||||
template <typename ClosureT>
|
||||
friend class closure_frame;
|
||||
|
||||
static closure_frame_t*&
|
||||
closure_frame_ref(closure_frame_t** frame_ = 0)
|
||||
{
|
||||
static closure_frame_t** frame = 0;
|
||||
if (frame_ != 0)
|
||||
frame = frame_;
|
||||
return *frame;
|
||||
}
|
||||
|
||||
closure_frame_t* frame;
|
||||
};
|
||||
|
||||
}}
|
||||
// namespace
|
||||
|
||||
#endif
|
||||
259
include/boost/lambda/construct.hpp
Normal file
259
include/boost/lambda/construct.hpp
Normal file
@@ -0,0 +1,259 @@
|
||||
// - construct.hpp -- Lambda Library -------------
|
||||
//
|
||||
// Copyright (C) 2000 Gary Powell (powellg@amazon.com)
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see http://www.boost.org
|
||||
//
|
||||
// -----------------------------------------------
|
||||
|
||||
#if !defined(BOOST_LAMBDA_CONSTRUCT_HPP)
|
||||
#define BOOST_LAMBDA_CONSTRUCT_HPP
|
||||
|
||||
#include "boost/type_traits/remove_cv.hpp"
|
||||
#include "boost/type_traits/is_pointer.hpp"
|
||||
#include "boost/config.hpp"
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) && !defined(BOOST_NO_CXX11_RVALUE_REFERENCES)
|
||||
#include <utility>
|
||||
#endif
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// constructor is used together with bind. constructor<A> creates a bindable
|
||||
// function object that passes its arguments forward to a constructor call
|
||||
// of type A
|
||||
|
||||
template<class T> struct constructor {
|
||||
|
||||
template <class U> struct sig { typedef T type; };
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) && !defined(BOOST_NO_CXX11_RVALUE_REFERENCES)
|
||||
template <class... Args>
|
||||
T operator()(Args&&... args) const {
|
||||
return T(std::forward<Args>(args)...);
|
||||
}
|
||||
#else
|
||||
T operator()() const {
|
||||
return T();
|
||||
}
|
||||
|
||||
template<class A1>
|
||||
T operator()(A1& a1) const {
|
||||
return T(a1);
|
||||
}
|
||||
|
||||
template<class A1, class A2>
|
||||
T operator()(A1& a1, A2& a2) const {
|
||||
return T(a1, a2);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3>
|
||||
T operator()(A1& a1, A2& a2, A3& a3) const {
|
||||
return T(a1, a2, a3);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4>
|
||||
T operator()(A1& a1, A2& a2, A3& a3, A4& a4) const {
|
||||
return T(a1, a2, a3, a4);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5>
|
||||
T operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) const {
|
||||
return T(a1, a2, a3, a4, a5);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
T operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) const {
|
||||
return T(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
T operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) const {
|
||||
return T(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
T operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8) const {
|
||||
return T(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9>
|
||||
T operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8, A9& a9) const {
|
||||
return T(a1, a2, a3, a4, a5, a6, a7, a8, a9);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9, class A10>
|
||||
T operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8, A9& a9, A10& a10) const {
|
||||
return T(a1, a2, a3, a4, a5, a6, a7, a8, a9, a10);
|
||||
}
|
||||
#endif
|
||||
|
||||
};
|
||||
|
||||
|
||||
namespace detail {
|
||||
|
||||
// A standard conforming compiler could disambiguate between
|
||||
// A1* and A1&, but not all compilers do that, so we need the
|
||||
// helpers
|
||||
|
||||
|
||||
template <bool IsPointer>
|
||||
struct destructor_helper {
|
||||
|
||||
template<class A1>
|
||||
static void exec(A1& a1) {
|
||||
// remove all the qualifiers, not sure whether it is necessary
|
||||
typedef typename boost::remove_cv<A1>::type plainA1;
|
||||
a1.~plainA1();
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct destructor_helper<true> {
|
||||
|
||||
template<class A1>
|
||||
static void exec(A1* a1) {
|
||||
typedef typename boost::remove_cv<A1>::type plainA1;
|
||||
(*a1).~plainA1();
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
// destructor funtion object
|
||||
struct destructor {
|
||||
|
||||
template <class T> struct sig { typedef void type; };
|
||||
|
||||
template<class A1>
|
||||
void operator()(A1& a1) const {
|
||||
typedef typename boost::remove_cv<A1>::type plainA1;
|
||||
detail::destructor_helper<boost::is_pointer<plainA1>::value>::exec(a1);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
|
||||
// new_ptr is used together with bind.
|
||||
|
||||
// note: placement new is not supported
|
||||
|
||||
template<class T> struct new_ptr {
|
||||
|
||||
template <class U> struct sig { typedef T* type; };
|
||||
|
||||
#if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) && !defined(BOOST_NO_CXX11_RVALUE_REFERENCES)
|
||||
template <class... Args>
|
||||
T* operator()(Args&&... args) const {
|
||||
return new T(std::forward<Args>(args)...);
|
||||
}
|
||||
#else
|
||||
T* operator()() const {
|
||||
return new T();
|
||||
}
|
||||
|
||||
template<class A1>
|
||||
T* operator()(A1& a1) const {
|
||||
return new T(a1);
|
||||
}
|
||||
|
||||
template<class A1, class A2>
|
||||
T* operator()(A1& a1, A2& a2) const {
|
||||
return new T(a1, a2);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3>
|
||||
T* operator()(A1& a1, A2& a2, A3& a3) const {
|
||||
return new T(a1, a2, a3);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4>
|
||||
T* operator()(A1& a1, A2& a2, A3& a3, A4& a4) const {
|
||||
return new T(a1, a2, a3, a4);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5>
|
||||
T* operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) const {
|
||||
return new T(a1, a2, a3, a4, a5);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
T* operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) const {
|
||||
return new T(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
T* operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) const {
|
||||
return new T(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
T* operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8) const {
|
||||
return new T(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9>
|
||||
T* operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8, A9& a9) const {
|
||||
return new T(a1, a2, a3, a4, a5, a6, a7, a8, a9);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9, class A10>
|
||||
T* operator()(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8, A9& a9, A10& a10) const {
|
||||
return new T(a1, a2, a3, a4, a5, a6, a7, a8, a9, a10);
|
||||
}
|
||||
#endif
|
||||
|
||||
};
|
||||
|
||||
// delete_ptr return void
|
||||
|
||||
struct delete_ptr {
|
||||
|
||||
template <class U> struct sig { typedef void type; };
|
||||
|
||||
template <class A1>
|
||||
void operator()(A1& a1) const {
|
||||
delete a1;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
|
||||
// new_array is used together with bind.
|
||||
|
||||
template<class T> struct new_array {
|
||||
|
||||
template <class U> struct sig { typedef T* type; };
|
||||
|
||||
T* operator()(int size) const {
|
||||
return new T[size];
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// delete_ptr return void
|
||||
|
||||
struct delete_array {
|
||||
|
||||
template <class U> struct sig { typedef void type; };
|
||||
|
||||
template <class A1>
|
||||
void operator()(A1& a1) const {
|
||||
delete[] a1;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
23
include/boost/lambda/control_structures.hpp
Normal file
23
include/boost/lambda/control_structures.hpp
Normal file
@@ -0,0 +1,23 @@
|
||||
// -- control_structures.hpp -- Boost Lambda Library --------------------------
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
#ifndef BOOST_LAMBDA_CONTROL_STRUCTURES_HPP
|
||||
#define BOOST_LAMBDA_CONTROL_STRUCTURES_HPP
|
||||
|
||||
|
||||
#include "boost/lambda/core.hpp"
|
||||
|
||||
// Arithmetic type promotion needed for if_then_else_return
|
||||
#include "boost/lambda/detail/operator_actions.hpp"
|
||||
#include "boost/lambda/detail/operator_return_type_traits.hpp"
|
||||
|
||||
#include "boost/lambda/if.hpp"
|
||||
#include "boost/lambda/loops.hpp"
|
||||
|
||||
#endif
|
||||
81
include/boost/lambda/core.hpp
Normal file
81
include/boost/lambda/core.hpp
Normal file
@@ -0,0 +1,81 @@
|
||||
// -- core.hpp -- Boost Lambda Library -------------------------------------
|
||||
//
|
||||
// Copyright (C) 2000 Gary Powell (powellg@amazon.com)
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
//
|
||||
// Includes the core of LL, without any real features for client:
|
||||
//
|
||||
// tuples, lambda functors, return type deduction templates,
|
||||
// argument substitution mechanism (select functions)
|
||||
//
|
||||
// Some functionality comes as well:
|
||||
// Assignment and subscript operators, as well as function
|
||||
// call operator for placeholder variables.
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_CORE_HPP
|
||||
#define BOOST_LAMBDA_CORE_HPP
|
||||
|
||||
#include "boost/config.hpp"
|
||||
|
||||
#include "boost/type_traits/transform_traits.hpp"
|
||||
#include "boost/type_traits/cv_traits.hpp"
|
||||
|
||||
#include "boost/tuple/tuple.hpp"
|
||||
|
||||
// inject some of the tuple names into lambda
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
using ::boost::tuples::tuple;
|
||||
using ::boost::tuples::null_type;
|
||||
|
||||
} // lambda
|
||||
} // boost
|
||||
|
||||
#include "boost/lambda/detail/lambda_config.hpp"
|
||||
#include "boost/lambda/detail/lambda_fwd.hpp"
|
||||
|
||||
#include "boost/lambda/detail/arity_code.hpp"
|
||||
#include "boost/lambda/detail/actions.hpp"
|
||||
|
||||
#include "boost/lambda/detail/lambda_traits.hpp"
|
||||
|
||||
#include "boost/lambda/detail/function_adaptors.hpp"
|
||||
#include "boost/lambda/detail/return_type_traits.hpp"
|
||||
|
||||
#include "boost/lambda/detail/select_functions.hpp"
|
||||
|
||||
#include "boost/lambda/detail/lambda_functor_base.hpp"
|
||||
|
||||
#include "boost/lambda/detail/lambda_functors.hpp"
|
||||
|
||||
#include "boost/lambda/detail/ret.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
namespace {
|
||||
|
||||
// These are constants types and need to be initialised
|
||||
boost::lambda::placeholder1_type free1 = boost::lambda::placeholder1_type();
|
||||
boost::lambda::placeholder2_type free2 = boost::lambda::placeholder2_type();
|
||||
boost::lambda::placeholder3_type free3 = boost::lambda::placeholder3_type();
|
||||
|
||||
boost::lambda::placeholder1_type& BOOST_ATTRIBUTE_UNUSED _1 = free1;
|
||||
boost::lambda::placeholder2_type& BOOST_ATTRIBUTE_UNUSED _2 = free2;
|
||||
boost::lambda::placeholder3_type& BOOST_ATTRIBUTE_UNUSED _3 = free3;
|
||||
// _1, _2, ... naming scheme by Peter Dimov
|
||||
} // unnamed
|
||||
|
||||
} // lambda
|
||||
} // boost
|
||||
|
||||
|
||||
#endif //BOOST_LAMBDA_CORE_HPP
|
||||
174
include/boost/lambda/detail/actions.hpp
Normal file
174
include/boost/lambda/detail/actions.hpp
Normal file
@@ -0,0 +1,174 @@
|
||||
// -- Boost Lambda Library - actions.hpp ----------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// ----------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_ACTIONS_HPP
|
||||
#define BOOST_LAMBDA_ACTIONS_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
|
||||
|
||||
template<int Arity, class Act> class action;
|
||||
|
||||
// these need to be defined here, since the corresponding lambda
|
||||
// functions are members of lambda_functor classes
|
||||
|
||||
class assignment_action {};
|
||||
class subscript_action {};
|
||||
|
||||
template <class Action> class other_action;
|
||||
|
||||
// action for specifying the explicit return type
|
||||
template <class RET> class explicit_return_type_action {};
|
||||
|
||||
// action for preventing the expansion of a lambda expression
|
||||
struct protect_action {};
|
||||
|
||||
// must be defined here, comma is a special case
|
||||
struct comma_action {};
|
||||
|
||||
|
||||
// actions, for which the existence of protect is checked in return type
|
||||
// deduction.
|
||||
|
||||
template <class Action> struct is_protectable {
|
||||
BOOST_STATIC_CONSTANT(bool, value = false);
|
||||
};
|
||||
|
||||
// NOTE: comma action is protectable. Other protectable actions
|
||||
// are listed in operator_actions.hpp
|
||||
|
||||
template<> struct is_protectable<other_action<comma_action> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
|
||||
|
||||
namespace detail {
|
||||
|
||||
// this type is used in return type deductions to signal that deduction
|
||||
// did not find a result. It does not necessarily mean an error, it commonly
|
||||
// means that something else should be tried.
|
||||
class unspecified {};
|
||||
}
|
||||
|
||||
// function action is a special case: bind functions can be called with
|
||||
// the return type specialized explicitly e.g. bind<int>(foo);
|
||||
// If this call syntax is used, the return type is stored in the latter
|
||||
// argument of function_action template. Otherwise the argument gets the type
|
||||
// 'unspecified'.
|
||||
// This argument is only relevant in the return type deduction code
|
||||
template <int I, class Result_type = detail::unspecified>
|
||||
class function_action {};
|
||||
|
||||
template<class T> class function_action<1, T> {
|
||||
public:
|
||||
template<class RET, class A1>
|
||||
static RET apply(A1& a1) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<2, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2>
|
||||
static RET apply(A1& a1, A2& a2) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<3, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2, class A3>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2, a3);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<4, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2, class A3, class A4>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2, a3, a4);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<5, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2, a3, a4, a5);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<6, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<7, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<8, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7,
|
||||
A8& a8) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<9, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8, class A9>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7,
|
||||
A8& a8, A9& a9) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2, a3, a4, a5, a6, a7, a8, a9);
|
||||
}
|
||||
};
|
||||
|
||||
template<class T> class function_action<10, T> {
|
||||
public:
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8, class A9, class A10>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7,
|
||||
A8& a8, A9& a9, A10& a10) {
|
||||
return function_adaptor<typename boost::remove_cv<A1>::type>::
|
||||
template apply<RET>(a1, a2, a3, a4, a5, a6, a7, a8, a9, a10);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
110
include/boost/lambda/detail/arity_code.hpp
Normal file
110
include/boost/lambda/detail/arity_code.hpp
Normal file
@@ -0,0 +1,110 @@
|
||||
// -- Boost Lambda Library -------------------------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// --------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_ARITY_CODE_HPP
|
||||
#define BOOST_LAMBDA_ARITY_CODE_HPP
|
||||
|
||||
#include "boost/type_traits/cv_traits.hpp"
|
||||
#include "boost/type_traits/transform_traits.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// These constants state, whether a lambda_functor instantiation results from
|
||||
// an expression which contains no placeholders (NONE),
|
||||
// only free1 placeholders (FIRST),
|
||||
// free2 placeholders and maybe free1 placeholders (SECOND),
|
||||
// free3 and maybe free1 and free2 placeholders (THIRD),
|
||||
// freeE placeholders and maybe free1 and free2 (EXCEPTION).
|
||||
// RETHROW means, that a rethrow expression is used somewhere in the lambda_functor.
|
||||
|
||||
enum { NONE = 0x00, // Notice we are using bits as flags here.
|
||||
FIRST = 0x01,
|
||||
SECOND = 0x02,
|
||||
THIRD = 0x04,
|
||||
EXCEPTION = 0x08,
|
||||
RETHROW = 0x10};
|
||||
|
||||
|
||||
template<class T>
|
||||
struct get_tuple_arity;
|
||||
|
||||
namespace detail {
|
||||
|
||||
template <class T> struct get_arity_;
|
||||
|
||||
} // end detail;
|
||||
|
||||
template <class T> struct get_arity {
|
||||
|
||||
BOOST_STATIC_CONSTANT(int, value = detail::get_arity_<typename boost::remove_cv<typename boost::remove_reference<T>::type>::type>::value);
|
||||
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
template<class T>
|
||||
struct get_arity_ {
|
||||
BOOST_STATIC_CONSTANT(int, value = 0);
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct get_arity_<lambda_functor<T> > {
|
||||
BOOST_STATIC_CONSTANT(int, value = get_arity<T>::value);
|
||||
};
|
||||
|
||||
template<class Action, class Args>
|
||||
struct get_arity_<lambda_functor_base<Action, Args> > {
|
||||
BOOST_STATIC_CONSTANT(int, value = get_tuple_arity<Args>::value);
|
||||
};
|
||||
|
||||
template<int I>
|
||||
struct get_arity_<placeholder<I> > {
|
||||
BOOST_STATIC_CONSTANT(int, value = I);
|
||||
};
|
||||
|
||||
} // detail
|
||||
|
||||
template<class T>
|
||||
struct get_tuple_arity {
|
||||
BOOST_STATIC_CONSTANT(int, value = get_arity<typename T::head_type>::value | get_tuple_arity<typename T::tail_type>::value);
|
||||
};
|
||||
|
||||
|
||||
template<>
|
||||
struct get_tuple_arity<null_type> {
|
||||
BOOST_STATIC_CONSTANT(int, value = 0);
|
||||
};
|
||||
|
||||
|
||||
// Does T have placeholder<I> as it's subexpression?
|
||||
|
||||
template<class T, int I>
|
||||
struct has_placeholder {
|
||||
BOOST_STATIC_CONSTANT(bool, value = (get_arity<T>::value & I) != 0);
|
||||
};
|
||||
|
||||
template<int I, int J>
|
||||
struct includes_placeholder {
|
||||
BOOST_STATIC_CONSTANT(bool, value = (J & I) != 0);
|
||||
};
|
||||
|
||||
template<int I, int J>
|
||||
struct lacks_placeholder {
|
||||
BOOST_STATIC_CONSTANT(bool, value = ((J & I) == 0));
|
||||
};
|
||||
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
1879
include/boost/lambda/detail/bind_functions.hpp
Normal file
1879
include/boost/lambda/detail/bind_functions.hpp
Normal file
File diff suppressed because it is too large
Load Diff
50
include/boost/lambda/detail/control_constructs_common.hpp
Normal file
50
include/boost/lambda/detail/control_constructs_common.hpp
Normal file
@@ -0,0 +1,50 @@
|
||||
// Boost Lambda Library -- control_constructs_common.hpp -------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// --------------------------------------------------------------------------
|
||||
|
||||
#if !defined(BOOST_CONTROL_CONSTRUCTS_COMMON_HPP)
|
||||
#define BOOST_CONTROL_CONSTRUCTS_COMMON_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// special types of lambda functors, used with control structures
|
||||
// to guarantee that they are composed correctly.
|
||||
|
||||
template<class Tag, class LambdaFunctor>
|
||||
class tagged_lambda_functor;
|
||||
|
||||
template<class Tag, class Args>
|
||||
class tagged_lambda_functor<Tag, lambda_functor<Args> >
|
||||
: public lambda_functor<Args>
|
||||
{
|
||||
public:
|
||||
tagged_lambda_functor(const Args& a) : lambda_functor<Args>(a) {}
|
||||
|
||||
tagged_lambda_functor(const lambda_functor<Args>& a)
|
||||
: lambda_functor<Args>(a) {}
|
||||
|
||||
// for the no body cases in control structures.
|
||||
tagged_lambda_functor() : lambda_functor<Args>() {}
|
||||
};
|
||||
|
||||
} // lambda
|
||||
} // boost
|
||||
|
||||
#endif // BOOST_CONTROL_CONSTRUCTS_COMMON_HPP
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
789
include/boost/lambda/detail/function_adaptors.hpp
Normal file
789
include/boost/lambda/detail/function_adaptors.hpp
Normal file
@@ -0,0 +1,789 @@
|
||||
// Boost Lambda Library - function_adaptors.hpp ----------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
|
||||
#ifndef BOOST_LAMBDA_FUNCTION_ADAPTORS_HPP
|
||||
#define BOOST_LAMBDA_FUNCTION_ADAPTORS_HPP
|
||||
|
||||
#include "boost/mpl/has_xxx.hpp"
|
||||
#include "boost/tuple/tuple.hpp"
|
||||
#include "boost/type_traits/same_traits.hpp"
|
||||
#include "boost/type_traits/remove_reference.hpp"
|
||||
#include "boost/type_traits/remove_cv.hpp"
|
||||
#include "boost/type_traits/add_const.hpp"
|
||||
#include "boost/type_traits/add_volatile.hpp"
|
||||
#include "boost/utility/result_of.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
namespace detail {
|
||||
|
||||
BOOST_MPL_HAS_XXX_TEMPLATE_DEF(sig)
|
||||
|
||||
template<class Tuple>
|
||||
struct remove_references_from_elements {
|
||||
typedef typename boost::tuples::cons<
|
||||
typename boost::remove_reference<typename Tuple::head_type>::type,
|
||||
typename remove_references_from_elements<typename Tuple::tail_type>::type
|
||||
> type;
|
||||
};
|
||||
|
||||
template<>
|
||||
struct remove_references_from_elements<boost::tuples::null_type> {
|
||||
typedef boost::tuples::null_type type;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
template <class Func> struct function_adaptor {
|
||||
|
||||
typedef typename detail::remove_reference_and_cv<Func>::type plainF;
|
||||
|
||||
#if !defined(BOOST_NO_RESULT_OF)
|
||||
// Support functors that use the boost::result_of return type convention.
|
||||
template<class Tuple, int Length, bool HasSig>
|
||||
struct result_converter;
|
||||
template<class Tuple, int Length>
|
||||
struct result_converter<Tuple, Length, true>
|
||||
: plainF::template sig<
|
||||
typename detail::remove_references_from_elements<Tuple>::type
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 0, false>
|
||||
: result_of<plainF()>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 1, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 2, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type,
|
||||
typename tuples::element<2, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 3, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type,
|
||||
typename tuples::element<2, Tuple>::type,
|
||||
typename tuples::element<3, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 4, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type,
|
||||
typename tuples::element<2, Tuple>::type,
|
||||
typename tuples::element<3, Tuple>::type,
|
||||
typename tuples::element<4, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 5, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type,
|
||||
typename tuples::element<2, Tuple>::type,
|
||||
typename tuples::element<3, Tuple>::type,
|
||||
typename tuples::element<4, Tuple>::type,
|
||||
typename tuples::element<5, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 6, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type,
|
||||
typename tuples::element<2, Tuple>::type,
|
||||
typename tuples::element<3, Tuple>::type,
|
||||
typename tuples::element<4, Tuple>::type,
|
||||
typename tuples::element<5, Tuple>::type,
|
||||
typename tuples::element<6, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 7, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type,
|
||||
typename tuples::element<2, Tuple>::type,
|
||||
typename tuples::element<3, Tuple>::type,
|
||||
typename tuples::element<4, Tuple>::type,
|
||||
typename tuples::element<5, Tuple>::type,
|
||||
typename tuples::element<6, Tuple>::type,
|
||||
typename tuples::element<7, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 8, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type,
|
||||
typename tuples::element<2, Tuple>::type,
|
||||
typename tuples::element<3, Tuple>::type,
|
||||
typename tuples::element<4, Tuple>::type,
|
||||
typename tuples::element<5, Tuple>::type,
|
||||
typename tuples::element<6, Tuple>::type,
|
||||
typename tuples::element<7, Tuple>::type,
|
||||
typename tuples::element<8, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
template<class Tuple>
|
||||
struct result_converter<Tuple, 9, false>
|
||||
: result_of<plainF(
|
||||
typename tuples::element<1, Tuple>::type,
|
||||
typename tuples::element<2, Tuple>::type,
|
||||
typename tuples::element<3, Tuple>::type,
|
||||
typename tuples::element<4, Tuple>::type,
|
||||
typename tuples::element<5, Tuple>::type,
|
||||
typename tuples::element<6, Tuple>::type,
|
||||
typename tuples::element<7, Tuple>::type,
|
||||
typename tuples::element<8, Tuple>::type,
|
||||
typename tuples::element<9, Tuple>::type)
|
||||
>
|
||||
{};
|
||||
|
||||
// we do not know the return type off-hand, we must ask it from Func
|
||||
// To sig we pass a cons list, where the head is the function object type
|
||||
// itself (potentially cv-qualified)
|
||||
// and the tail contains the types of the actual arguments to be passed
|
||||
// to the function object. The arguments can be cv qualified
|
||||
// as well.
|
||||
template <class Args>
|
||||
struct sig
|
||||
: result_converter<
|
||||
Args
|
||||
, tuples::length<typename Args::tail_type>::value
|
||||
, detail::has_sig<plainF>::value
|
||||
>
|
||||
{};
|
||||
#else // BOOST_NO_RESULT_OF
|
||||
|
||||
template <class Args> class sig {
|
||||
typedef typename detail::remove_reference_and_cv<Func>::type plainF;
|
||||
public:
|
||||
typedef typename plainF::template sig<
|
||||
typename detail::remove_references_from_elements<Args>::type
|
||||
>::type type;
|
||||
};
|
||||
#endif
|
||||
|
||||
template<class RET, class A1>
|
||||
static RET apply(A1& a1) {
|
||||
return a1();
|
||||
}
|
||||
template<class RET, class A1, class A2>
|
||||
static RET apply(A1& a1, A2& a2) {
|
||||
return a1(a2);
|
||||
}
|
||||
template<class RET, class A1, class A2, class A3>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3) {
|
||||
return a1(a2, a3);
|
||||
}
|
||||
template<class RET, class A1, class A2, class A3, class A4>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4) {
|
||||
return a1(a2, a3, a4);
|
||||
}
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) {
|
||||
return a1(a2, a3, a4, a5);
|
||||
}
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) {
|
||||
return a1(a2, a3, a4, a5, a6);
|
||||
}
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5, class A6,
|
||||
class A7>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6,
|
||||
A7& a7) {
|
||||
return a1(a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5, class A6,
|
||||
class A7, class A8>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6,
|
||||
A7& a7, A8& a8) {
|
||||
return a1(a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5, class A6,
|
||||
class A7, class A8, class A9>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6,
|
||||
A7& a7, A8& a8, A9& a9) {
|
||||
return a1(a2, a3, a4, a5, a6, a7, a8, a9);
|
||||
}
|
||||
template<class RET, class A1, class A2, class A3, class A4, class A5, class A6,
|
||||
class A7, class A8, class A9, class A10>
|
||||
static RET apply(A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6,
|
||||
A7& a7, A8& a8, A9& a9, A10& a10) {
|
||||
return a1(a2, a3, a4, a5, a6, a7, a8, a9, a10);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Func> struct function_adaptor<const Func>; // error
|
||||
|
||||
// -- function adaptors with data member access
|
||||
template <class Object, class T>
|
||||
struct function_adaptor<T Object::*> {
|
||||
|
||||
// typedef detail::unspecified type;
|
||||
|
||||
// T can have qualifiers and can be a reference type
|
||||
// We get the return type by adding const, if the object through which
|
||||
// the data member is accessed is const, and finally adding a reference
|
||||
template<class Args> class sig {
|
||||
typedef typename boost::tuples::element<1, Args>::type argument_type;
|
||||
typedef typename boost::remove_reference<
|
||||
argument_type
|
||||
>::type unref_type;
|
||||
|
||||
typedef typename detail::IF<boost::is_const<unref_type>::value,
|
||||
typename boost::add_const<T>::type,
|
||||
T
|
||||
>::RET properly_consted_return_type;
|
||||
|
||||
typedef typename detail::IF<boost::is_volatile<unref_type>::value,
|
||||
typename boost::add_volatile<properly_consted_return_type>::type,
|
||||
properly_consted_return_type
|
||||
>::RET properly_cvd_return_type;
|
||||
|
||||
|
||||
public:
|
||||
typedef typename detail::IF<boost::is_reference<argument_type>::value,
|
||||
typename boost::add_reference<properly_cvd_return_type>::type,
|
||||
typename boost::remove_cv<T>::type
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
template <class RET>
|
||||
static RET apply( T Object::*data, Object& o) {
|
||||
return o.*data;
|
||||
}
|
||||
template <class RET>
|
||||
static RET apply( T Object::*data, const Object& o) {
|
||||
return o.*data;
|
||||
}
|
||||
template <class RET>
|
||||
static RET apply( T Object::*data, volatile Object& o) {
|
||||
return o.*data;
|
||||
}
|
||||
template <class RET>
|
||||
static RET apply( T Object::*data, const volatile Object& o) {
|
||||
return o.*data;
|
||||
}
|
||||
template <class RET>
|
||||
static RET apply( T Object::*data, Object* o) {
|
||||
return o->*data;
|
||||
}
|
||||
template <class RET>
|
||||
static RET apply( T Object::*data, const Object* o) {
|
||||
return o->*data;
|
||||
}
|
||||
template <class RET>
|
||||
static RET apply( T Object::*data, volatile Object* o) {
|
||||
return o->*data;
|
||||
}
|
||||
template <class RET>
|
||||
static RET apply( T Object::*data, const volatile Object* o) {
|
||||
return o->*data;
|
||||
}
|
||||
};
|
||||
|
||||
// -- function adaptors with 1 argument apply
|
||||
|
||||
template <class Result>
|
||||
struct function_adaptor<Result (void)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET>
|
||||
static Result apply(Result (*func)()) {
|
||||
return func();
|
||||
}
|
||||
};
|
||||
|
||||
template <class Result>
|
||||
struct function_adaptor<Result (*)(void)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET>
|
||||
static Result apply(Result (*func)()) {
|
||||
return func();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 2 argument apply
|
||||
template <class Object, class Result>
|
||||
struct function_adaptor<Result (Object::*)() const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET>
|
||||
static Result apply( Result (Object::*func)() const, const Object* o) {
|
||||
return (o->*func)();
|
||||
}
|
||||
template <class RET>
|
||||
static Result apply( Result (Object::*func)() const, const Object& o) {
|
||||
return (o.*func)();
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Result>
|
||||
struct function_adaptor<Result (Object::*)()> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET>
|
||||
static Result apply( Result (Object::*func)(), Object* o) {
|
||||
return (o->*func)();
|
||||
}
|
||||
template <class RET>
|
||||
static Result apply( Result (Object::*func)(), Object& o) {
|
||||
return (o.*func)();
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Result>
|
||||
struct function_adaptor<Result (Arg1)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1>
|
||||
static Result apply(Result (*func)(Arg1), A1& a1) {
|
||||
return func(a1);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1>
|
||||
static Result apply(Result (*func)(Arg1), A1& a1) {
|
||||
return func(a1);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 3 argument apply
|
||||
template <class Object, class Arg1, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1) const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1>
|
||||
static Result apply( Result (Object::*func)(Arg1) const, const Object* o,
|
||||
A1& a1) {
|
||||
return (o->*func)(a1);
|
||||
}
|
||||
template <class RET, class A1>
|
||||
static Result apply( Result (Object::*func)(Arg1) const, const Object& o,
|
||||
A1& a1) {
|
||||
return (o.*func)(a1);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Arg1, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1>
|
||||
static Result apply( Result (Object::*func)(Arg1), Object* o, A1& a1) {
|
||||
return (o->*func)(a1);
|
||||
}
|
||||
template <class RET, class A1>
|
||||
static Result apply( Result (Object::*func)(Arg1), Object& o, A1& a1) {
|
||||
return (o.*func)(a1);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Result>
|
||||
struct function_adaptor<Result (Arg1, Arg2)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2>
|
||||
static Result apply(Result (*func)(Arg1, Arg2), A1& a1, A2& a2) {
|
||||
return func(a1, a2);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1, Arg2)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2>
|
||||
static Result apply(Result (*func)(Arg1, Arg2), A1& a1, A2& a2) {
|
||||
return func(a1, a2);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 4 argument apply
|
||||
template <class Object, class Arg1, class Arg2, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2) const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2) const, const Object* o, A1& a1, A2& a2) {
|
||||
return (o->*func)(a1, a2);
|
||||
}
|
||||
template <class RET, class A1, class A2>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2) const, const Object& o, A1& a1, A2& a2) {
|
||||
return (o.*func)(a1, a2);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Arg1, class Arg2, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2), Object* o, A1& a1, A2& a2) {
|
||||
return (o->*func)(a1, a2);
|
||||
}
|
||||
template <class RET, class A1, class A2>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2), Object& o, A1& a1, A2& a2) {
|
||||
return (o.*func)(a1, a2);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Result>
|
||||
struct function_adaptor<Result (Arg1, Arg2, Arg3)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3), A1& a1, A2& a2, A3& a3) {
|
||||
return func(a1, a2, a3);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1, Arg2, Arg3)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3), A1& a1, A2& a2, A3& a3) {
|
||||
return func(a1, a2, a3);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 5 argument apply
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3) const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3) const, const Object* o, A1& a1, A2& a2, A3& a3) {
|
||||
return (o->*func)(a1, a2, a3);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3) const, const Object& o, A1& a1, A2& a2, A3& a3) {
|
||||
return (o.*func)(a1, a2, a3);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3), Object* o, A1& a1, A2& a2, A3& a3) {
|
||||
return (o->*func)(a1, a2, a3);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3), Object& o, A1& a1, A2& a2, A3& a3) {
|
||||
return (o.*func)(a1, a2, a3);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Result>
|
||||
struct function_adaptor<Result (Arg1, Arg2, Arg3, Arg4)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4), A1& a1, A2& a2, A3& a3, A4& a4) {
|
||||
return func(a1, a2, a3, a4);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1, Arg2, Arg3, Arg4)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4), A1& a1, A2& a2, A3& a3, A4& a4) {
|
||||
return func(a1, a2, a3, a4);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 6 argument apply
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4) const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4) const, const Object* o, A1& a1, A2& a2, A3& a3, A4& a4) {
|
||||
return (o->*func)(a1, a2, a3, a4);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4) const, const Object& o, A1& a1, A2& a2, A3& a3, A4& a4) {
|
||||
return (o.*func)(a1, a2, a3, a4);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4), Object* o, A1& a1, A2& a2, A3& a3, A4& a4) {
|
||||
return (o->*func)(a1, a2, a3, a4);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4), Object& o, A1& a1, A2& a2, A3& a3, A4& a4) {
|
||||
return (o.*func)(a1, a2, a3, a4);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Result>
|
||||
struct function_adaptor<Result (Arg1, Arg2, Arg3, Arg4, Arg5)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) {
|
||||
return func(a1, a2, a3, a4, a5);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1, Arg2, Arg3, Arg4, Arg5)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) {
|
||||
return func(a1, a2, a3, a4, a5);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 7 argument apply
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4, Arg5) const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5) const, const Object* o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) {
|
||||
return (o->*func)(a1, a2, a3, a4, a5);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5) const, const Object& o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) {
|
||||
return (o.*func)(a1, a2, a3, a4, a5);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4, Arg5)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5), Object* o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) {
|
||||
return (o->*func)(a1, a2, a3, a4, a5);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5), Object& o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5) {
|
||||
return (o.*func)(a1, a2, a3, a4, a5);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Result>
|
||||
struct function_adaptor<Result (Arg1, Arg2, Arg3, Arg4, Arg5, Arg6)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) {
|
||||
return func(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) {
|
||||
return func(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 8 argument apply
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6) const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6) const, const Object* o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) {
|
||||
return (o->*func)(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6) const, const Object& o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) {
|
||||
return (o.*func)(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6), Object* o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) {
|
||||
return (o->*func)(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6), Object& o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6) {
|
||||
return (o.*func)(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Result>
|
||||
struct function_adaptor<Result (Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) {
|
||||
return func(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) {
|
||||
return func(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 9 argument apply
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7) const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7) const, const Object* o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) {
|
||||
return (o->*func)(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7) const, const Object& o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) {
|
||||
return (o.*func)(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7), Object* o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) {
|
||||
return (o->*func)(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7), Object& o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7) {
|
||||
return (o.*func)(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Arg8, class Result>
|
||||
struct function_adaptor<Result (Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8) {
|
||||
return func(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Arg8, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8) {
|
||||
return func(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// -- function adaptors with 10 argument apply
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Arg8, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8) const> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8) const, const Object* o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8) {
|
||||
return (o->*func)(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8) const, const Object& o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8) {
|
||||
return (o.*func)(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Object, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Arg8, class Result>
|
||||
struct function_adaptor<Result (Object::*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8), Object* o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8) {
|
||||
return (o->*func)(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
static Result apply( Result (Object::*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8), Object& o, A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8) {
|
||||
return (o.*func)(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Arg8, class Arg9, class Result>
|
||||
struct function_adaptor<Result (Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8, Arg9)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8, Arg9), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8, A9& a9) {
|
||||
return func(a1, a2, a3, a4, a5, a6, a7, a8, a9);
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Arg8, class Arg9, class Result>
|
||||
struct function_adaptor<Result (*)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8, Arg9)> {
|
||||
|
||||
template<class T> struct sig { typedef Result type; };
|
||||
template <class RET, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9>
|
||||
static Result apply(Result (*func)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8, Arg9), A1& a1, A2& a2, A3& a3, A4& a4, A5& a5, A6& a6, A7& a7, A8& a8, A9& a9) {
|
||||
return func(a1, a2, a3, a4, a5, a6, a7, a8, a9);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
104
include/boost/lambda/detail/is_instance_of.hpp
Normal file
104
include/boost/lambda/detail/is_instance_of.hpp
Normal file
@@ -0,0 +1,104 @@
|
||||
// Boost Lambda Library - is_instance_of.hpp ---------------------
|
||||
|
||||
// Copyright (C) 2001 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// ---------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_IS_INSTANCE_OF
|
||||
#define BOOST_LAMBDA_IS_INSTANCE_OF
|
||||
|
||||
#include "boost/config.hpp" // for BOOST_STATIC_CONSTANT
|
||||
#include "boost/type_traits/conversion_traits.hpp" // for is_convertible
|
||||
#include "boost/preprocessor/enum_shifted_params.hpp"
|
||||
#include "boost/preprocessor/repeat_2nd.hpp"
|
||||
|
||||
// is_instance_of --------------------------------
|
||||
//
|
||||
// is_instance_of_n<A, B>::value is true, if type A is
|
||||
// an instantiation of a template B, or A derives from an instantiation
|
||||
// of template B
|
||||
//
|
||||
// n is the number of template arguments for B
|
||||
//
|
||||
// Example:
|
||||
// is_instance_of_2<std::istream, basic_stream>::value == true
|
||||
|
||||
// The original implementation was somewhat different, with different versions
|
||||
// for different compilers. However, there was still a problem
|
||||
// with gcc.3.0.2 and 3.0.3 compilers, which didn't think regard
|
||||
// is_instance_of_N<...>::value was a constant.
|
||||
// John Maddock suggested the way around this problem by building
|
||||
// is_instance_of templates using boost::is_convertible.
|
||||
// Now we only have one version of is_instance_of templates, which delagate
|
||||
// all the nasty compiler tricks to is_convertible.
|
||||
|
||||
#define BOOST_LAMBDA_CLASS(z, N,A) BOOST_PP_COMMA_IF(N) class
|
||||
#define BOOST_LAMBDA_CLASS_ARG(z, N,A) BOOST_PP_COMMA_IF(N) class A##N
|
||||
#define BOOST_LAMBDA_ARG(z, N,A) BOOST_PP_COMMA_IF(N) A##N
|
||||
|
||||
#define BOOST_LAMBDA_CLASS_LIST(n, NAME) BOOST_PP_REPEAT(n, BOOST_LAMBDA_CLASS, NAME)
|
||||
|
||||
#define BOOST_LAMBDA_CLASS_ARG_LIST(n, NAME) BOOST_PP_REPEAT(n, BOOST_LAMBDA_CLASS_ARG, NAME)
|
||||
|
||||
#define BOOST_LAMBDA_ARG_LIST(n, NAME) BOOST_PP_REPEAT(n, BOOST_LAMBDA_ARG, NAME)
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
#define BOOST_LAMBDA_IS_INSTANCE_OF_TEMPLATE(INDEX) \
|
||||
\
|
||||
namespace detail { \
|
||||
\
|
||||
template <template<BOOST_LAMBDA_CLASS_LIST(INDEX,T)> class F> \
|
||||
struct BOOST_PP_CAT(conversion_tester_,INDEX) { \
|
||||
template<BOOST_LAMBDA_CLASS_ARG_LIST(INDEX,A)> \
|
||||
BOOST_PP_CAT(conversion_tester_,INDEX) \
|
||||
(const F<BOOST_LAMBDA_ARG_LIST(INDEX,A)>&); \
|
||||
}; \
|
||||
\
|
||||
} /* end detail */ \
|
||||
\
|
||||
template <class From, template <BOOST_LAMBDA_CLASS_LIST(INDEX,T)> class To> \
|
||||
struct BOOST_PP_CAT(is_instance_of_,INDEX) \
|
||||
{ \
|
||||
private: \
|
||||
typedef ::boost::is_convertible< \
|
||||
From, \
|
||||
BOOST_PP_CAT(detail::conversion_tester_,INDEX)<To> \
|
||||
> helper_type; \
|
||||
\
|
||||
public: \
|
||||
BOOST_STATIC_CONSTANT(bool, value = helper_type::value); \
|
||||
};
|
||||
|
||||
|
||||
#define BOOST_LAMBDA_HELPER(z, N, A) BOOST_LAMBDA_IS_INSTANCE_OF_TEMPLATE( BOOST_PP_INC(N) )
|
||||
|
||||
// Generate the traits for 1-4 argument templates
|
||||
|
||||
BOOST_PP_REPEAT_2ND(4,BOOST_LAMBDA_HELPER,FOO)
|
||||
|
||||
#undef BOOST_LAMBDA_HELPER
|
||||
#undef BOOST_LAMBDA_IS_INSTANCE_OF_TEMPLATE
|
||||
#undef BOOST_LAMBDA_CLASS
|
||||
#undef BOOST_LAMBDA_ARG
|
||||
#undef BOOST_LAMBDA_CLASS_ARG
|
||||
#undef BOOST_LAMBDA_CLASS_LIST
|
||||
#undef BOOST_LAMBDA_ARG_LIST
|
||||
#undef BOOST_LAMBDA_CLASS_ARG_LIST
|
||||
|
||||
} // lambda
|
||||
} // boost
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
41
include/boost/lambda/detail/lambda_config.hpp
Normal file
41
include/boost/lambda/detail/lambda_config.hpp
Normal file
@@ -0,0 +1,41 @@
|
||||
// Boost Lambda Library - lambda_config.hpp ------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// ---------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_LAMBDA_CONFIG_HPP
|
||||
#define BOOST_LAMBDA_LAMBDA_CONFIG_HPP
|
||||
|
||||
// add to boost/config.hpp
|
||||
// for now
|
||||
|
||||
|
||||
# if defined __GNUC__
|
||||
# if (__GNUC__ == 3 && __GNUC_MINOR__ >= 4)
|
||||
# define BOOST_REF_TO_FUNC_CONFLICTS_WITH_REF_TO_T
|
||||
# define BOOST_LAMBDA_INCORRECT_BIND_OVERLOADING
|
||||
# endif
|
||||
# endif // __GNUC__
|
||||
|
||||
|
||||
#if defined __KCC
|
||||
|
||||
#define BOOST_NO_FDECL_TEMPLATES_AS_TEMPLATE_TEMPLATE_PARAMS
|
||||
|
||||
#endif // __KCC
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
615
include/boost/lambda/detail/lambda_functor_base.hpp
Normal file
615
include/boost/lambda/detail/lambda_functor_base.hpp
Normal file
@@ -0,0 +1,615 @@
|
||||
// Boost Lambda Library lambda_functor_base.hpp -----------------------------
|
||||
//
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// ------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_HPP
|
||||
#define BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_HPP
|
||||
|
||||
#include "boost/type_traits/add_reference.hpp"
|
||||
#include "boost/type_traits/add_const.hpp"
|
||||
#include "boost/type_traits/remove_const.hpp"
|
||||
#include "boost/lambda/detail/lambda_fwd.hpp"
|
||||
#include "boost/lambda/detail/lambda_traits.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC, >= 1400)
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4512) //assignment operator could not be generated
|
||||
#endif
|
||||
|
||||
// for return type deductions we wrap bound argument to this class,
|
||||
// which fulfils the base class contract for lambda_functors
|
||||
template <class T>
|
||||
class identity {
|
||||
|
||||
T elem;
|
||||
public:
|
||||
|
||||
typedef T element_t;
|
||||
|
||||
// take all parameters as const references. Note that non-const references
|
||||
// stay as they are.
|
||||
typedef typename boost::add_reference<
|
||||
typename boost::add_const<T>::type
|
||||
>::type par_t;
|
||||
|
||||
explicit identity(par_t t) : elem(t) {}
|
||||
|
||||
template <typename SigArgs>
|
||||
struct sig { typedef typename boost::remove_const<element_t>::type type; };
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const { CALL_USE_ARGS; return elem; }
|
||||
};
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC, >= 1400)
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
template <class T>
|
||||
inline lambda_functor<identity<T&> > var(T& t) { return identity<T&>(t); }
|
||||
|
||||
// for lambda functors, var is an identity operator. It was forbidden
|
||||
// at some point, but we might want to var something that can be a
|
||||
// non-lambda functor or a lambda functor.
|
||||
template <class T>
|
||||
lambda_functor<T> var(const lambda_functor<T>& t) { return t; }
|
||||
|
||||
template <class T> struct var_type {
|
||||
typedef lambda_functor<identity<T&> > type;
|
||||
};
|
||||
|
||||
|
||||
template <class T>
|
||||
inline
|
||||
lambda_functor<identity<typename bound_argument_conversion<const T>::type> >
|
||||
constant(const T& t) {
|
||||
return identity<typename bound_argument_conversion<const T>::type>(t);
|
||||
}
|
||||
template <class T>
|
||||
lambda_functor<T> constant(const lambda_functor<T>& t) { return t; }
|
||||
|
||||
template <class T> struct constant_type {
|
||||
typedef
|
||||
lambda_functor<
|
||||
identity<typename bound_argument_conversion<const T>::type>
|
||||
> type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
template <class T>
|
||||
inline lambda_functor<identity<const T&> > constant_ref(const T& t) {
|
||||
return identity<const T&>(t);
|
||||
}
|
||||
template <class T>
|
||||
lambda_functor<T> constant_ref(const lambda_functor<T>& t) { return t; }
|
||||
|
||||
template <class T> struct constant_ref_type {
|
||||
typedef
|
||||
lambda_functor<identity<const T&> > type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
// as_lambda_functor turns any types to lambda functors
|
||||
// non-lambda_functors will be bound argument types
|
||||
template <class T>
|
||||
struct as_lambda_functor {
|
||||
typedef typename
|
||||
detail::remove_reference_and_cv<T>::type plain_T;
|
||||
typedef typename
|
||||
detail::IF<is_lambda_functor<plain_T>::value,
|
||||
plain_T,
|
||||
lambda_functor<
|
||||
identity<typename bound_argument_conversion<T>::type>
|
||||
>
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
// turns arbitrary objects into lambda functors
|
||||
template <class T>
|
||||
inline
|
||||
lambda_functor<identity<typename bound_argument_conversion<const T>::type> >
|
||||
to_lambda_functor(const T& t) {
|
||||
return identity<typename bound_argument_conversion<const T>::type>(t);
|
||||
}
|
||||
|
||||
template <class T>
|
||||
inline lambda_functor<T>
|
||||
to_lambda_functor(const lambda_functor<T>& t) {
|
||||
return t;
|
||||
}
|
||||
|
||||
namespace detail {
|
||||
|
||||
|
||||
|
||||
// In a call constify_rvals<T>::go(x)
|
||||
// x should be of type T. If T is a non-reference type, do
|
||||
// returns x as const reference.
|
||||
// Otherwise the type doesn't change.
|
||||
// The purpose of this class is to avoid
|
||||
// 'cannot bind temporaries to non-const references' errors.
|
||||
template <class T> struct constify_rvals {
|
||||
template<class U>
|
||||
static inline const U& go(const U& u) { return u; }
|
||||
};
|
||||
|
||||
template <class T> struct constify_rvals<T&> {
|
||||
template<class U>
|
||||
static inline U& go(U& u) { return u; }
|
||||
};
|
||||
|
||||
// check whether one of the elements of a tuple (cons list) is of type
|
||||
// null_type. Needed, because the compiler goes ahead and instantiates
|
||||
// sig template for nullary case even if the nullary operator() is not
|
||||
// called
|
||||
template <class T> struct is_null_type
|
||||
{ BOOST_STATIC_CONSTANT(bool, value = false); };
|
||||
|
||||
template <> struct is_null_type<null_type>
|
||||
{ BOOST_STATIC_CONSTANT(bool, value = true); };
|
||||
|
||||
template<class Tuple> struct has_null_type {
|
||||
BOOST_STATIC_CONSTANT(bool, value = (is_null_type<typename Tuple::head_type>::value || has_null_type<typename Tuple::tail_type>::value));
|
||||
};
|
||||
template<> struct has_null_type<null_type> {
|
||||
BOOST_STATIC_CONSTANT(bool, value = false);
|
||||
};
|
||||
|
||||
|
||||
// helpers -------------------
|
||||
|
||||
|
||||
template<class Args, class SigArgs>
|
||||
class deduce_argument_types_ {
|
||||
typedef typename as_lambda_functor<typename Args::head_type>::type lf_t;
|
||||
typedef typename lf_t::inherited::template sig<SigArgs>::type el_t;
|
||||
public:
|
||||
typedef
|
||||
boost::tuples::cons<
|
||||
el_t,
|
||||
typename deduce_argument_types_<typename Args::tail_type, SigArgs>::type
|
||||
> type;
|
||||
};
|
||||
|
||||
template<class SigArgs>
|
||||
class deduce_argument_types_<null_type, SigArgs> {
|
||||
public:
|
||||
typedef null_type type;
|
||||
};
|
||||
|
||||
|
||||
// // note that tuples cannot have plain function types as elements.
|
||||
// // Hence, all other types will be non-const, except references to
|
||||
// // functions.
|
||||
// template <class T> struct remove_reference_except_from_functions {
|
||||
// typedef typename boost::remove_reference<T>::type t;
|
||||
// typedef typename detail::IF<boost::is_function<t>::value, T, t>::RET type;
|
||||
// };
|
||||
|
||||
template<class Args, class SigArgs>
|
||||
class deduce_non_ref_argument_types_ {
|
||||
typedef typename as_lambda_functor<typename Args::head_type>::type lf_t;
|
||||
typedef typename lf_t::inherited::template sig<SigArgs>::type el_t;
|
||||
public:
|
||||
typedef
|
||||
boost::tuples::cons<
|
||||
// typename detail::remove_reference_except_from_functions<el_t>::type,
|
||||
typename boost::remove_reference<el_t>::type,
|
||||
typename deduce_non_ref_argument_types_<typename Args::tail_type, SigArgs>::type
|
||||
> type;
|
||||
};
|
||||
|
||||
template<class SigArgs>
|
||||
class deduce_non_ref_argument_types_<null_type, SigArgs> {
|
||||
public:
|
||||
typedef null_type type;
|
||||
};
|
||||
|
||||
// -------------
|
||||
|
||||
// take stored Args and Open Args, and return a const list with
|
||||
// deduced elements (real return types)
|
||||
template<class Args, class SigArgs>
|
||||
class deduce_argument_types {
|
||||
typedef typename deduce_argument_types_<Args, SigArgs>::type t1;
|
||||
public:
|
||||
typedef typename detail::IF<
|
||||
has_null_type<t1>::value, null_type, t1
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
// take stored Args and Open Args, and return a const list with
|
||||
// deduced elements (references are stripped from the element types)
|
||||
|
||||
template<class Args, class SigArgs>
|
||||
class deduce_non_ref_argument_types {
|
||||
typedef typename deduce_non_ref_argument_types_<Args, SigArgs>::type t1;
|
||||
public:
|
||||
typedef typename detail::IF<
|
||||
has_null_type<t1>::value, null_type, t1
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
template <int N, class Args, class SigArgs>
|
||||
struct nth_return_type_sig {
|
||||
typedef typename
|
||||
as_lambda_functor<
|
||||
typename boost::tuples::element<N, Args>::type
|
||||
// typename tuple_element_as_reference<N, Args>::type
|
||||
>::type lf_type;
|
||||
|
||||
typedef typename lf_type::inherited::template sig<SigArgs>::type type;
|
||||
};
|
||||
|
||||
template<int N, class Tuple> struct element_or_null {
|
||||
typedef typename boost::tuples::element<N, Tuple>::type type;
|
||||
};
|
||||
|
||||
template<int N> struct element_or_null<N, null_type> {
|
||||
typedef null_type type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
} // end detail
|
||||
|
||||
// -- lambda_functor base ---------------------
|
||||
|
||||
// the explicit_return_type_action case -----------------------------------
|
||||
template<class RET, class Args>
|
||||
class lambda_functor_base<explicit_return_type_action<RET>, Args>
|
||||
{
|
||||
public:
|
||||
Args args;
|
||||
|
||||
typedef RET result_type;
|
||||
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template <class SigArgs> struct sig { typedef RET type; };
|
||||
|
||||
template<class RET_, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const
|
||||
{
|
||||
return detail::constify_rvals<RET>::go(
|
||||
detail::r_select<RET>::go(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS));
|
||||
}
|
||||
};
|
||||
|
||||
// the protect_action case -----------------------------------
|
||||
template<class Args>
|
||||
class lambda_functor_base<protect_action, Args>
|
||||
{
|
||||
public:
|
||||
Args args;
|
||||
public:
|
||||
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const
|
||||
{
|
||||
CALL_USE_ARGS;
|
||||
return boost::tuples::get<0>(args);
|
||||
}
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
// typedef typename detail::tuple_element_as_reference<0, SigArgs>::type type;
|
||||
typedef typename boost::tuples::element<0, Args>::type type;
|
||||
};
|
||||
};
|
||||
|
||||
// Do nothing --------------------------------------------------------
|
||||
class do_nothing_action {};
|
||||
|
||||
template<class Args>
|
||||
class lambda_functor_base<do_nothing_action, Args> {
|
||||
// Args args;
|
||||
public:
|
||||
// explicit lambda_functor_base(const Args& a) {}
|
||||
lambda_functor_base() {}
|
||||
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS> RET call(CALL_FORMAL_ARGS) const {
|
||||
return CALL_USE_ARGS;
|
||||
}
|
||||
|
||||
template<class SigArgs> struct sig { typedef void type; };
|
||||
};
|
||||
|
||||
|
||||
// These specializations provide a shorter notation to define actions.
|
||||
// These lambda_functor_base instances take care of the recursive evaluation
|
||||
// of the arguments and pass the evaluated arguments to the apply function
|
||||
// of an action class. To make action X work with these classes, one must
|
||||
// instantiate the lambda_functor_base as:
|
||||
// lambda_functor_base<action<ARITY, X>, Args>
|
||||
// Where ARITY is the arity of the apply function in X
|
||||
|
||||
// The return type is queried as:
|
||||
// return_type_N<X, EvaluatedArgumentTypes>::type
|
||||
// for which there must be a specialization.
|
||||
|
||||
// Function actions, casts, throws,... all go via these classes.
|
||||
|
||||
|
||||
template<class Act, class Args>
|
||||
class lambda_functor_base<action<0, Act>, Args>
|
||||
{
|
||||
public:
|
||||
// Args args; not needed
|
||||
explicit lambda_functor_base(const Args& /*a*/) {}
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
typedef typename return_type_N<Act, null_type>::type type;
|
||||
};
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
CALL_USE_ARGS;
|
||||
return Act::template apply<RET>();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
#if defined BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART
|
||||
#error "Multiple defines of BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART"
|
||||
#endif
|
||||
|
||||
|
||||
#define BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(ARITY) \
|
||||
template<class Act, class Args> \
|
||||
class lambda_functor_base<action<ARITY, Act>, Args> \
|
||||
{ \
|
||||
public: \
|
||||
Args args; \
|
||||
\
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {} \
|
||||
\
|
||||
template<class SigArgs> struct sig { \
|
||||
typedef typename \
|
||||
detail::deduce_argument_types<Args, SigArgs>::type rets_t; \
|
||||
public: \
|
||||
typedef typename \
|
||||
return_type_N_prot<Act, rets_t>::type type; \
|
||||
}; \
|
||||
\
|
||||
\
|
||||
template<class RET, CALL_TEMPLATE_ARGS> \
|
||||
RET call(CALL_FORMAL_ARGS) const { \
|
||||
using boost::tuples::get; \
|
||||
using detail::constify_rvals; \
|
||||
using detail::r_select; \
|
||||
using detail::element_or_null; \
|
||||
using detail::deduce_argument_types;
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(1)
|
||||
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(2)
|
||||
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(3)
|
||||
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
typedef typename element_or_null<2, rets_t>::type rt2;
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt2>::go(r_select<rt2>::go(get<2>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(4)
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
typedef typename element_or_null<2, rets_t>::type rt2;
|
||||
typedef typename element_or_null<3, rets_t>::type rt3;
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt2>::go(r_select<rt2>::go(get<2>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt3>::go(r_select<rt3>::go(get<3>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(5)
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
typedef typename element_or_null<2, rets_t>::type rt2;
|
||||
typedef typename element_or_null<3, rets_t>::type rt3;
|
||||
typedef typename element_or_null<4, rets_t>::type rt4;
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt2>::go(r_select<rt2>::go(get<2>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt3>::go(r_select<rt3>::go(get<3>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt4>::go(r_select<rt4>::go(get<4>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(6)
|
||||
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
typedef typename element_or_null<2, rets_t>::type rt2;
|
||||
typedef typename element_or_null<3, rets_t>::type rt3;
|
||||
typedef typename element_or_null<4, rets_t>::type rt4;
|
||||
typedef typename element_or_null<5, rets_t>::type rt5;
|
||||
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt2>::go(r_select<rt2>::go(get<2>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt3>::go(r_select<rt3>::go(get<3>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt4>::go(r_select<rt4>::go(get<4>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt5>::go(r_select<rt5>::go(get<5>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(7)
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
typedef typename element_or_null<2, rets_t>::type rt2;
|
||||
typedef typename element_or_null<3, rets_t>::type rt3;
|
||||
typedef typename element_or_null<4, rets_t>::type rt4;
|
||||
typedef typename element_or_null<5, rets_t>::type rt5;
|
||||
typedef typename element_or_null<6, rets_t>::type rt6;
|
||||
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt2>::go(r_select<rt2>::go(get<2>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt3>::go(r_select<rt3>::go(get<3>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt4>::go(r_select<rt4>::go(get<4>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt5>::go(r_select<rt5>::go(get<5>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt6>::go(r_select<rt6>::go(get<6>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(8)
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
typedef typename element_or_null<2, rets_t>::type rt2;
|
||||
typedef typename element_or_null<3, rets_t>::type rt3;
|
||||
typedef typename element_or_null<4, rets_t>::type rt4;
|
||||
typedef typename element_or_null<5, rets_t>::type rt5;
|
||||
typedef typename element_or_null<6, rets_t>::type rt6;
|
||||
typedef typename element_or_null<7, rets_t>::type rt7;
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt2>::go(r_select<rt2>::go(get<2>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt3>::go(r_select<rt3>::go(get<3>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt4>::go(r_select<rt4>::go(get<4>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt5>::go(r_select<rt5>::go(get<5>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt6>::go(r_select<rt6>::go(get<6>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt7>::go(r_select<rt7>::go(get<7>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(9)
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
typedef typename element_or_null<2, rets_t>::type rt2;
|
||||
typedef typename element_or_null<3, rets_t>::type rt3;
|
||||
typedef typename element_or_null<4, rets_t>::type rt4;
|
||||
typedef typename element_or_null<5, rets_t>::type rt5;
|
||||
typedef typename element_or_null<6, rets_t>::type rt6;
|
||||
typedef typename element_or_null<7, rets_t>::type rt7;
|
||||
typedef typename element_or_null<8, rets_t>::type rt8;
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt2>::go(r_select<rt2>::go(get<2>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt3>::go(r_select<rt3>::go(get<3>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt4>::go(r_select<rt4>::go(get<4>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt5>::go(r_select<rt5>::go(get<5>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt6>::go(r_select<rt6>::go(get<6>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt7>::go(r_select<rt7>::go(get<7>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt8>::go(r_select<rt8>::go(get<8>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART(10)
|
||||
typedef typename
|
||||
deduce_argument_types<Args, tuple<CALL_REFERENCE_TYPES> >::type rets_t;
|
||||
typedef typename element_or_null<0, rets_t>::type rt0;
|
||||
typedef typename element_or_null<1, rets_t>::type rt1;
|
||||
typedef typename element_or_null<2, rets_t>::type rt2;
|
||||
typedef typename element_or_null<3, rets_t>::type rt3;
|
||||
typedef typename element_or_null<4, rets_t>::type rt4;
|
||||
typedef typename element_or_null<5, rets_t>::type rt5;
|
||||
typedef typename element_or_null<6, rets_t>::type rt6;
|
||||
typedef typename element_or_null<7, rets_t>::type rt7;
|
||||
typedef typename element_or_null<8, rets_t>::type rt8;
|
||||
typedef typename element_or_null<9, rets_t>::type rt9;
|
||||
|
||||
return Act::template apply<RET>(
|
||||
constify_rvals<rt0>::go(r_select<rt0>::go(get<0>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt1>::go(r_select<rt1>::go(get<1>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt2>::go(r_select<rt2>::go(get<2>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt3>::go(r_select<rt3>::go(get<3>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt4>::go(r_select<rt4>::go(get<4>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt5>::go(r_select<rt5>::go(get<5>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt6>::go(r_select<rt6>::go(get<6>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt7>::go(r_select<rt7>::go(get<7>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt8>::go(r_select<rt8>::go(get<8>(args), CALL_ACTUAL_ARGS)),
|
||||
constify_rvals<rt9>::go(r_select<rt9>::go(get<9>(args), CALL_ACTUAL_ARGS))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
#undef BOOST_LAMBDA_LAMBDA_FUNCTOR_BASE_FIRST_PART
|
||||
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
357
include/boost/lambda/detail/lambda_functors.hpp
Normal file
357
include/boost/lambda/detail/lambda_functors.hpp
Normal file
@@ -0,0 +1,357 @@
|
||||
// Boost Lambda Library - lambda_functors.hpp -------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see http://www.boost.org
|
||||
|
||||
// ------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_LAMBDA_FUNCTORS_HPP
|
||||
#define BOOST_LAMBDA_LAMBDA_FUNCTORS_HPP
|
||||
|
||||
#include <boost/config.hpp>
|
||||
#include <boost/detail/workaround.hpp>
|
||||
#include <boost/utility/result_of.hpp>
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC, == 1310)
|
||||
|
||||
#include <boost/mpl/or.hpp>
|
||||
#include <boost/utility/enable_if.hpp>
|
||||
#include <boost/type_traits/is_array.hpp>
|
||||
|
||||
#define BOOST_LAMBDA_DISABLE_IF_ARRAY1(A1, R1)\
|
||||
typename lazy_disable_if<is_array<A1>, typename R1 >::type
|
||||
#define BOOST_LAMBDA_DISABLE_IF_ARRAY2(A1, A2, R1, R2) \
|
||||
typename lazy_disable_if<mpl::or_<is_array<A1>, is_array<A2> >, typename R1, R2 >::type
|
||||
#define BOOST_LAMBDA_DISABLE_IF_ARRAY3(A1, A2, A3, R1, R2, R3) \
|
||||
typename lazy_disable_if<mpl::or_<is_array<A1>, is_array<A2>, is_array<A3> >, typename R1, R2, R3 >::type
|
||||
|
||||
#else
|
||||
|
||||
#define BOOST_LAMBDA_DISABLE_IF_ARRAY1(A1, R1) typename R1::type
|
||||
#define BOOST_LAMBDA_DISABLE_IF_ARRAY2(A1, A2, R1, R2) typename R1, R2::type
|
||||
#define BOOST_LAMBDA_DISABLE_IF_ARRAY3(A1, A2, A3, R1, R2, R3) typename R1, R2, R3::type
|
||||
|
||||
#endif
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// -- lambda_functor --------------------------------------------
|
||||
// --------------------------------------------------------------
|
||||
|
||||
//inline const null_type const_null_type() { return null_type(); }
|
||||
|
||||
namespace detail {
|
||||
namespace {
|
||||
|
||||
static const null_type constant_null_type = null_type();
|
||||
|
||||
} // unnamed
|
||||
} // detail
|
||||
|
||||
class unused {};
|
||||
|
||||
#define cnull_type() detail::constant_null_type
|
||||
|
||||
// -- free variables types --------------------------------------------------
|
||||
|
||||
// helper to work around the case where the nullary return type deduction
|
||||
// is always performed, even though the functor is not nullary
|
||||
namespace detail {
|
||||
template<int N, class Tuple> struct get_element_or_null_type {
|
||||
typedef typename
|
||||
detail::tuple_element_as_reference<N, Tuple>::type type;
|
||||
};
|
||||
template<int N> struct get_element_or_null_type<N, null_type> {
|
||||
typedef null_type type;
|
||||
};
|
||||
}
|
||||
|
||||
template <int I> struct placeholder;
|
||||
|
||||
template<> struct placeholder<FIRST> {
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
typedef typename detail::get_element_or_null_type<0, SigArgs>::type type;
|
||||
};
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
BOOST_STATIC_ASSERT(boost::is_reference<RET>::value);
|
||||
CALL_USE_ARGS; // does nothing, prevents warnings for unused args
|
||||
return a;
|
||||
}
|
||||
};
|
||||
|
||||
template<> struct placeholder<SECOND> {
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
typedef typename detail::get_element_or_null_type<1, SigArgs>::type type;
|
||||
};
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const { CALL_USE_ARGS; return b; }
|
||||
};
|
||||
|
||||
template<> struct placeholder<THIRD> {
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
typedef typename detail::get_element_or_null_type<2, SigArgs>::type type;
|
||||
};
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const { CALL_USE_ARGS; return c; }
|
||||
};
|
||||
|
||||
template<> struct placeholder<EXCEPTION> {
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
typedef typename detail::get_element_or_null_type<3, SigArgs>::type type;
|
||||
};
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const { CALL_USE_ARGS; return env; }
|
||||
};
|
||||
|
||||
typedef const lambda_functor<placeholder<FIRST> > placeholder1_type;
|
||||
typedef const lambda_functor<placeholder<SECOND> > placeholder2_type;
|
||||
typedef const lambda_functor<placeholder<THIRD> > placeholder3_type;
|
||||
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
// free variables are lambda_functors. This is to allow uniform handling with
|
||||
// other lambda_functors.
|
||||
// -------------------------------------------------------------------
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC, >= 1400)
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4512) //assignment operator could not be generated
|
||||
#endif
|
||||
|
||||
// -- lambda_functor NONE ------------------------------------------------
|
||||
template <class T>
|
||||
class lambda_functor : public T
|
||||
{
|
||||
|
||||
BOOST_STATIC_CONSTANT(int, arity_bits = get_arity<T>::value);
|
||||
|
||||
public:
|
||||
typedef T inherited;
|
||||
|
||||
lambda_functor() {}
|
||||
lambda_functor(const lambda_functor& l) : inherited(l) {}
|
||||
|
||||
lambda_functor(const T& t) : inherited(t) {}
|
||||
|
||||
template <class SigArgs> struct sig {
|
||||
typedef typename inherited::template
|
||||
sig<typename SigArgs::tail_type>::type type;
|
||||
};
|
||||
|
||||
// Note that this return type deduction template is instantiated, even
|
||||
// if the nullary
|
||||
// operator() is not called at all. One must make sure that it does not fail.
|
||||
typedef typename
|
||||
inherited::template sig<null_type>::type
|
||||
nullary_return_type;
|
||||
|
||||
// Support for boost::result_of.
|
||||
template <class Sig> struct result;
|
||||
template <class F>
|
||||
struct result<F()> {
|
||||
typedef nullary_return_type type;
|
||||
};
|
||||
template <class F, class A>
|
||||
struct result<F(A)> {
|
||||
typedef typename sig<tuple<F, A> >::type type;
|
||||
};
|
||||
template <class F, class A, class B>
|
||||
struct result<F(A, B)> {
|
||||
typedef typename sig<tuple<F, A, B> >::type type;
|
||||
};
|
||||
template <class F, class A, class B, class C>
|
||||
struct result<F(A, B, C)> {
|
||||
typedef typename sig<tuple<F, A, B, C> >::type type;
|
||||
};
|
||||
|
||||
nullary_return_type operator()() const {
|
||||
return inherited::template
|
||||
call<nullary_return_type>
|
||||
(cnull_type(), cnull_type(), cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A>
|
||||
typename inherited::template sig<tuple<A&> >::type
|
||||
operator()(A& a) const {
|
||||
return inherited::template call<
|
||||
typename inherited::template sig<tuple<A&> >::type
|
||||
>(a, cnull_type(), cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A>
|
||||
BOOST_LAMBDA_DISABLE_IF_ARRAY1(A, inherited::template sig<tuple<A const&> >)
|
||||
operator()(A const& a) const {
|
||||
return inherited::template call<
|
||||
typename inherited::template sig<tuple<A const&> >::type
|
||||
>(a, cnull_type(), cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
typename inherited::template sig<tuple<A&, B&> >::type
|
||||
operator()(A& a, B& b) const {
|
||||
return inherited::template call<
|
||||
typename inherited::template sig<tuple<A&, B&> >::type
|
||||
>(a, b, cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
BOOST_LAMBDA_DISABLE_IF_ARRAY2(A, B, inherited::template sig<tuple<A const&, B&> >)
|
||||
operator()(A const& a, B& b) const {
|
||||
return inherited::template call<
|
||||
typename inherited::template sig<tuple<A const&, B&> >::type
|
||||
>(a, b, cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
BOOST_LAMBDA_DISABLE_IF_ARRAY2(A, B, inherited::template sig<tuple<A&, B const&> >)
|
||||
operator()(A& a, B const& b) const {
|
||||
return inherited::template call<
|
||||
typename inherited::template sig<tuple<A&, B const&> >::type
|
||||
>(a, b, cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
BOOST_LAMBDA_DISABLE_IF_ARRAY2(A, B, inherited::template sig<tuple<A const&, B const&> >)
|
||||
operator()(A const& a, B const& b) const {
|
||||
return inherited::template call<
|
||||
typename inherited::template sig<tuple<A const&, B const&> >::type
|
||||
>(a, b, cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B, class C>
|
||||
typename inherited::template sig<tuple<A&, B&, C&> >::type
|
||||
operator()(A& a, B& b, C& c) const
|
||||
{
|
||||
return inherited::template call<
|
||||
typename inherited::template sig<tuple<A&, B&, C&> >::type
|
||||
>(a, b, c, cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B, class C>
|
||||
BOOST_LAMBDA_DISABLE_IF_ARRAY3(A, B, C, inherited::template sig<tuple<A const&, B const&, C const&> >)
|
||||
operator()(A const& a, B const& b, C const& c) const
|
||||
{
|
||||
return inherited::template call<
|
||||
typename inherited::template sig<tuple<A const&, B const&, C const&> >::type
|
||||
>(a, b, c, cnull_type());
|
||||
}
|
||||
|
||||
// for internal calls with env
|
||||
template<CALL_TEMPLATE_ARGS>
|
||||
typename inherited::template sig<tuple<CALL_REFERENCE_TYPES> >::type
|
||||
internal_call(CALL_FORMAL_ARGS) const {
|
||||
return inherited::template
|
||||
call<typename inherited::template
|
||||
sig<tuple<CALL_REFERENCE_TYPES> >::type>(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
|
||||
template<class A>
|
||||
const lambda_functor<lambda_functor_base<
|
||||
other_action<assignment_action>,
|
||||
boost::tuple<lambda_functor,
|
||||
typename const_copy_argument <const A>::type> > >
|
||||
operator=(const A& a) const {
|
||||
return lambda_functor_base<
|
||||
other_action<assignment_action>,
|
||||
boost::tuple<lambda_functor,
|
||||
typename const_copy_argument <const A>::type> >
|
||||
( boost::tuple<lambda_functor,
|
||||
typename const_copy_argument <const A>::type>(*this, a) );
|
||||
}
|
||||
|
||||
template<class A>
|
||||
const lambda_functor<lambda_functor_base<
|
||||
other_action<subscript_action>,
|
||||
boost::tuple<lambda_functor,
|
||||
typename const_copy_argument <const A>::type> > >
|
||||
operator[](const A& a) const {
|
||||
return lambda_functor_base<
|
||||
other_action<subscript_action>,
|
||||
boost::tuple<lambda_functor,
|
||||
typename const_copy_argument <const A>::type> >
|
||||
( boost::tuple<lambda_functor,
|
||||
typename const_copy_argument <const A>::type>(*this, a ) );
|
||||
}
|
||||
};
|
||||
|
||||
#if BOOST_WORKAROUND(BOOST_MSVC, >= 1400)
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
namespace boost {
|
||||
|
||||
#if !defined(BOOST_RESULT_OF_USE_DECLTYPE) || defined(BOOST_NO_CXX11_DECLTYPE)
|
||||
|
||||
template<class T>
|
||||
struct result_of<boost::lambda::lambda_functor<T>()>
|
||||
{
|
||||
typedef typename boost::lambda::lambda_functor<T>::nullary_return_type type;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct result_of<const boost::lambda::lambda_functor<T>()>
|
||||
{
|
||||
typedef typename boost::lambda::lambda_functor<T>::nullary_return_type type;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
template<class T>
|
||||
struct tr1_result_of<boost::lambda::lambda_functor<T>()>
|
||||
{
|
||||
typedef typename boost::lambda::lambda_functor<T>::nullary_return_type type;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct tr1_result_of<const boost::lambda::lambda_functor<T>()>
|
||||
{
|
||||
typedef typename boost::lambda::lambda_functor<T>::nullary_return_type type;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
// is_placeholder
|
||||
|
||||
#include <boost/is_placeholder.hpp>
|
||||
|
||||
namespace boost
|
||||
{
|
||||
|
||||
template<> struct is_placeholder< lambda::lambda_functor< lambda::placeholder<lambda::FIRST> > >
|
||||
{
|
||||
enum _vt { value = 1 };
|
||||
};
|
||||
|
||||
template<> struct is_placeholder< lambda::lambda_functor< lambda::placeholder<lambda::SECOND> > >
|
||||
{
|
||||
enum _vt { value = 2 };
|
||||
};
|
||||
|
||||
template<> struct is_placeholder< lambda::lambda_functor< lambda::placeholder<lambda::THIRD> > >
|
||||
{
|
||||
enum _vt { value = 3 };
|
||||
};
|
||||
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
74
include/boost/lambda/detail/lambda_fwd.hpp
Normal file
74
include/boost/lambda/detail/lambda_fwd.hpp
Normal file
@@ -0,0 +1,74 @@
|
||||
// lambda_fwd.hpp - Boost Lambda Library -------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// -------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_FWD_HPP
|
||||
#define BOOST_LAMBDA_FWD_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
namespace detail {
|
||||
|
||||
template<class T> struct generate_error;
|
||||
|
||||
}
|
||||
// -- placeholders --------------------------------------------
|
||||
|
||||
template <int I> struct placeholder;
|
||||
|
||||
// function_adaptors
|
||||
template <class Func>
|
||||
struct function_adaptor;
|
||||
|
||||
template <int I, class Act> class action;
|
||||
|
||||
template <class Base>
|
||||
class lambda_functor;
|
||||
|
||||
template <class Act, class Args>
|
||||
class lambda_functor_base;
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
|
||||
// #define CALL_TEMPLATE_ARGS class A, class Env
|
||||
// #define CALL_FORMAL_ARGS A& a, Env& env
|
||||
// #define CALL_ACTUAL_ARGS a, env
|
||||
// #define CALL_ACTUAL_ARGS_NO_ENV a
|
||||
// #define CALL_REFERENCE_TYPES A&, Env&
|
||||
// #define CALL_PLAIN_TYPES A, Env
|
||||
#define CALL_TEMPLATE_ARGS class A, class B, class C, class Env
|
||||
#define CALL_FORMAL_ARGS A& a, B& b, C& c, Env& env
|
||||
#define CALL_ACTUAL_ARGS a, b, c, env
|
||||
#define CALL_ACTUAL_ARGS_NO_ENV a, b, c
|
||||
#define CALL_REFERENCE_TYPES A&, B&, C&, Env&
|
||||
#define CALL_PLAIN_TYPES A, B, C, Env
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
namespace detail {
|
||||
|
||||
template<class A1, class A2, class A3, class A4>
|
||||
void do_nothing(A1&, A2&, A3&, A4&) {}
|
||||
|
||||
} // detail
|
||||
} // lambda
|
||||
} // boost
|
||||
|
||||
// prevent the warnings from unused arguments
|
||||
#define CALL_USE_ARGS \
|
||||
::boost::lambda::detail::do_nothing(a, b, c, env)
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
583
include/boost/lambda/detail/lambda_traits.hpp
Normal file
583
include/boost/lambda/detail/lambda_traits.hpp
Normal file
@@ -0,0 +1,583 @@
|
||||
// - lambda_traits.hpp --- Boost Lambda Library ----------------------------
|
||||
//
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_LAMBDA_TRAITS_HPP
|
||||
#define BOOST_LAMBDA_LAMBDA_TRAITS_HPP
|
||||
|
||||
#include "boost/type_traits/transform_traits.hpp"
|
||||
#include "boost/type_traits/cv_traits.hpp"
|
||||
#include "boost/type_traits/function_traits.hpp"
|
||||
#include "boost/type_traits/object_traits.hpp"
|
||||
#include "boost/tuple/tuple.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// -- if construct ------------------------------------------------
|
||||
// Proposed by Krzysztof Czarnecki and Ulrich Eisenecker
|
||||
|
||||
namespace detail {
|
||||
|
||||
template <bool If, class Then, class Else> struct IF { typedef Then RET; };
|
||||
|
||||
template <class Then, class Else> struct IF<false, Then, Else> {
|
||||
typedef Else RET;
|
||||
};
|
||||
|
||||
|
||||
// An if construct that doesn't instantiate the non-matching template:
|
||||
|
||||
// Called as:
|
||||
// IF_type<condition, A, B>::type
|
||||
// The matching template must define the typeded 'type'
|
||||
// I.e. A::type if condition is true, B::type if condition is false
|
||||
// Idea from Vesa Karvonen (from C&E as well I guess)
|
||||
template<class T>
|
||||
struct IF_type_
|
||||
{
|
||||
typedef typename T::type type;
|
||||
};
|
||||
|
||||
|
||||
template<bool C, class T, class E>
|
||||
struct IF_type
|
||||
{
|
||||
typedef typename
|
||||
IF_type_<typename IF<C, T, E>::RET >::type type;
|
||||
};
|
||||
|
||||
// helper that can be used to give typedef T to some type
|
||||
template <class T> struct identity_mapping { typedef T type; };
|
||||
|
||||
// An if construct for finding an integral constant 'value'
|
||||
// Does not instantiate the non-matching branch
|
||||
// Called as IF_value<condition, A, B>::value
|
||||
// If condition is true A::value must be defined, otherwise B::value
|
||||
|
||||
template<class T>
|
||||
struct IF_value_
|
||||
{
|
||||
BOOST_STATIC_CONSTANT(int, value = T::value);
|
||||
};
|
||||
|
||||
|
||||
template<bool C, class T, class E>
|
||||
struct IF_value
|
||||
{
|
||||
BOOST_STATIC_CONSTANT(int, value = (IF_value_<typename IF<C, T, E>::RET>::value));
|
||||
};
|
||||
|
||||
|
||||
// --------------------------------------------------------------
|
||||
|
||||
// removes reference from other than function types:
|
||||
template<class T> class remove_reference_if_valid
|
||||
{
|
||||
|
||||
typedef typename boost::remove_reference<T>::type plainT;
|
||||
public:
|
||||
typedef typename IF<
|
||||
boost::is_function<plainT>::value,
|
||||
T,
|
||||
plainT
|
||||
>::RET type;
|
||||
|
||||
};
|
||||
|
||||
|
||||
template<class T> struct remove_reference_and_cv {
|
||||
typedef typename boost::remove_cv<
|
||||
typename boost::remove_reference<T>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
// returns a reference to the element of tuple T
|
||||
template<int N, class T> struct tuple_element_as_reference {
|
||||
typedef typename
|
||||
boost::tuples::access_traits<
|
||||
typename boost::tuples::element<N, T>::type
|
||||
>::non_const_type type;
|
||||
};
|
||||
|
||||
// returns the cv and reverence stripped type of a tuple element
|
||||
template<int N, class T> struct tuple_element_stripped {
|
||||
typedef typename
|
||||
remove_reference_and_cv<
|
||||
typename boost::tuples::element<N, T>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// is_lambda_functor -------------------------------------------------
|
||||
|
||||
template <class T> struct is_lambda_functor_ {
|
||||
BOOST_STATIC_CONSTANT(bool, value = false);
|
||||
};
|
||||
|
||||
template <class Arg> struct is_lambda_functor_<lambda_functor<Arg> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
|
||||
} // end detail
|
||||
|
||||
|
||||
template <class T> struct is_lambda_functor {
|
||||
BOOST_STATIC_CONSTANT(bool,
|
||||
value =
|
||||
detail::is_lambda_functor_<
|
||||
typename detail::remove_reference_and_cv<T>::type
|
||||
>::value);
|
||||
};
|
||||
|
||||
|
||||
namespace detail {
|
||||
|
||||
// -- parameter_traits_ ---------------------------------------------
|
||||
|
||||
// An internal parameter type traits class that respects
|
||||
// the reference_wrapper class.
|
||||
|
||||
// The conversions performed are:
|
||||
// references -> compile_time_error
|
||||
// T1 -> T2,
|
||||
// reference_wrapper<T> -> T&
|
||||
// const array -> ref to const array
|
||||
// array -> ref to array
|
||||
// function -> ref to function
|
||||
|
||||
// ------------------------------------------------------------------------
|
||||
|
||||
template<class T1, class T2>
|
||||
struct parameter_traits_ {
|
||||
typedef T2 type;
|
||||
};
|
||||
|
||||
// Do not instantiate with reference types
|
||||
template<class T, class Any> struct parameter_traits_<T&, Any> {
|
||||
typedef typename
|
||||
generate_error<T&>::
|
||||
parameter_traits_class_instantiated_with_reference_type type;
|
||||
};
|
||||
|
||||
// Arrays can't be stored as plain types; convert them to references
|
||||
template<class T, int n, class Any> struct parameter_traits_<T[n], Any> {
|
||||
typedef T (&type)[n];
|
||||
};
|
||||
|
||||
template<class T, int n, class Any>
|
||||
struct parameter_traits_<const T[n], Any> {
|
||||
typedef const T (&type)[n];
|
||||
};
|
||||
|
||||
template<class T, int n, class Any>
|
||||
struct parameter_traits_<volatile T[n], Any> {
|
||||
typedef volatile T (&type)[n];
|
||||
};
|
||||
template<class T, int n, class Any>
|
||||
struct parameter_traits_<const volatile T[n], Any> {
|
||||
typedef const volatile T (&type)[n];
|
||||
};
|
||||
|
||||
|
||||
template<class T, class Any>
|
||||
struct parameter_traits_<boost::reference_wrapper<T>, Any >{
|
||||
typedef T& type;
|
||||
};
|
||||
|
||||
template<class T, class Any>
|
||||
struct parameter_traits_<const boost::reference_wrapper<T>, Any >{
|
||||
typedef T& type;
|
||||
};
|
||||
|
||||
template<class T, class Any>
|
||||
struct parameter_traits_<volatile boost::reference_wrapper<T>, Any >{
|
||||
typedef T& type;
|
||||
};
|
||||
|
||||
template<class T, class Any>
|
||||
struct parameter_traits_<const volatile boost::reference_wrapper<T>, Any >{
|
||||
typedef T& type;
|
||||
};
|
||||
|
||||
template<class Any>
|
||||
struct parameter_traits_<void, Any> {
|
||||
typedef void type;
|
||||
};
|
||||
|
||||
template<class Arg, class Any>
|
||||
struct parameter_traits_<lambda_functor<Arg>, Any > {
|
||||
typedef lambda_functor<Arg> type;
|
||||
};
|
||||
|
||||
template<class Arg, class Any>
|
||||
struct parameter_traits_<const lambda_functor<Arg>, Any > {
|
||||
typedef lambda_functor<Arg> type;
|
||||
};
|
||||
|
||||
// Are the volatile versions needed?
|
||||
template<class Arg, class Any>
|
||||
struct parameter_traits_<volatile lambda_functor<Arg>, Any > {
|
||||
typedef lambda_functor<Arg> type;
|
||||
};
|
||||
|
||||
template<class Arg, class Any>
|
||||
struct parameter_traits_<const volatile lambda_functor<Arg>, Any > {
|
||||
typedef lambda_functor<Arg> type;
|
||||
};
|
||||
|
||||
} // end namespace detail
|
||||
|
||||
|
||||
// ------------------------------------------------------------------------
|
||||
// traits classes for lambda expressions (bind functions, operators ...)
|
||||
|
||||
// must be instantiated with non-reference types
|
||||
|
||||
// The default is const plain type -------------------------
|
||||
// const T -> const T,
|
||||
// T -> const T,
|
||||
// references -> compile_time_error
|
||||
// reference_wrapper<T> -> T&
|
||||
// array -> const ref array
|
||||
template<class T>
|
||||
struct const_copy_argument {
|
||||
typedef typename
|
||||
detail::parameter_traits_<
|
||||
T,
|
||||
typename detail::IF<boost::is_function<T>::value, T&, const T>::RET
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// T may be a function type. Without the IF test, const would be added
|
||||
// to a function type, which is illegal.
|
||||
|
||||
// all arrays are converted to const.
|
||||
// This traits template is used for 'const T&' parameter passing
|
||||
// and thus the knowledge of the potential
|
||||
// non-constness of an actual argument is lost.
|
||||
template<class T, int n> struct const_copy_argument <T[n]> {
|
||||
typedef const T (&type)[n];
|
||||
};
|
||||
template<class T, int n> struct const_copy_argument <volatile T[n]> {
|
||||
typedef const volatile T (&type)[n];
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct const_copy_argument<T&> {};
|
||||
// do not instantiate with references
|
||||
// typedef typename detail::generate_error<T&>::references_not_allowed type;
|
||||
|
||||
|
||||
template<>
|
||||
struct const_copy_argument<void> {
|
||||
typedef void type;
|
||||
};
|
||||
|
||||
template<>
|
||||
struct const_copy_argument<void const> {
|
||||
typedef void type;
|
||||
};
|
||||
|
||||
|
||||
// Does the same as const_copy_argument, but passes references through as such
|
||||
template<class T>
|
||||
struct bound_argument_conversion {
|
||||
typedef typename const_copy_argument<T>::type type;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct bound_argument_conversion<T&> {
|
||||
typedef T& type;
|
||||
};
|
||||
|
||||
// The default is non-const reference -------------------------
|
||||
// const T -> const T&,
|
||||
// T -> T&,
|
||||
// references -> compile_time_error
|
||||
// reference_wrapper<T> -> T&
|
||||
template<class T>
|
||||
struct reference_argument {
|
||||
typedef typename detail::parameter_traits_<T, T&>::type type;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct reference_argument<T&> {
|
||||
typedef typename detail::generate_error<T&>::references_not_allowed type;
|
||||
};
|
||||
|
||||
template<class Arg>
|
||||
struct reference_argument<lambda_functor<Arg> > {
|
||||
typedef lambda_functor<Arg> type;
|
||||
};
|
||||
|
||||
template<class Arg>
|
||||
struct reference_argument<const lambda_functor<Arg> > {
|
||||
typedef lambda_functor<Arg> type;
|
||||
};
|
||||
|
||||
// Are the volatile versions needed?
|
||||
template<class Arg>
|
||||
struct reference_argument<volatile lambda_functor<Arg> > {
|
||||
typedef lambda_functor<Arg> type;
|
||||
};
|
||||
|
||||
template<class Arg>
|
||||
struct reference_argument<const volatile lambda_functor<Arg> > {
|
||||
typedef lambda_functor<Arg> type;
|
||||
};
|
||||
|
||||
template<>
|
||||
struct reference_argument<void> {
|
||||
typedef void type;
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
// Array to pointer conversion
|
||||
template <class T>
|
||||
struct array_to_pointer {
|
||||
typedef T type;
|
||||
};
|
||||
|
||||
template <class T, int N>
|
||||
struct array_to_pointer <const T[N]> {
|
||||
typedef const T* type;
|
||||
};
|
||||
template <class T, int N>
|
||||
struct array_to_pointer <T[N]> {
|
||||
typedef T* type;
|
||||
};
|
||||
|
||||
template <class T, int N>
|
||||
struct array_to_pointer <const T (&) [N]> {
|
||||
typedef const T* type;
|
||||
};
|
||||
template <class T, int N>
|
||||
struct array_to_pointer <T (&) [N]> {
|
||||
typedef T* type;
|
||||
};
|
||||
|
||||
|
||||
// ---------------------------------------------------------------------------
|
||||
// The call_traits for bind
|
||||
// Respects the reference_wrapper class.
|
||||
|
||||
// These templates are used outside of bind functions as well.
|
||||
// the bind_tuple_mapper provides a shorter notation for default
|
||||
// bound argument storing semantics, if all arguments are treated
|
||||
// uniformly.
|
||||
|
||||
// from template<class T> foo(const T& t) : bind_traits<const T>::type
|
||||
// from template<class T> foo(T& t) : bind_traits<T>::type
|
||||
|
||||
// Conversions:
|
||||
// T -> const T,
|
||||
// cv T -> cv T,
|
||||
// T& -> T&
|
||||
// reference_wrapper<T> -> T&
|
||||
// const reference_wrapper<T> -> T&
|
||||
// array -> const ref array
|
||||
|
||||
// make bound arguments const, this is a deliberate design choice, the
|
||||
// purpose is to prevent side effects to bound arguments that are stored
|
||||
// as copies
|
||||
template<class T>
|
||||
struct bind_traits {
|
||||
typedef const T type;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct bind_traits<T&> {
|
||||
typedef T& type;
|
||||
};
|
||||
|
||||
// null_types are an exception, we always want to store them as non const
|
||||
// so that other templates can assume that null_type is always without const
|
||||
template<>
|
||||
struct bind_traits<null_type> {
|
||||
typedef null_type type;
|
||||
};
|
||||
|
||||
// the bind_tuple_mapper, bind_type_generators may
|
||||
// introduce const to null_type
|
||||
template<>
|
||||
struct bind_traits<const null_type> {
|
||||
typedef null_type type;
|
||||
};
|
||||
|
||||
// Arrays can't be stored as plain types; convert them to references.
|
||||
// All arrays are converted to const. This is because bind takes its
|
||||
// parameters as const T& and thus the knowledge of the potential
|
||||
// non-constness of actual argument is lost.
|
||||
template<class T, int n> struct bind_traits <T[n]> {
|
||||
typedef const T (&type)[n];
|
||||
};
|
||||
|
||||
template<class T, int n>
|
||||
struct bind_traits<const T[n]> {
|
||||
typedef const T (&type)[n];
|
||||
};
|
||||
|
||||
template<class T, int n> struct bind_traits<volatile T[n]> {
|
||||
typedef const volatile T (&type)[n];
|
||||
};
|
||||
|
||||
template<class T, int n>
|
||||
struct bind_traits<const volatile T[n]> {
|
||||
typedef const volatile T (&type)[n];
|
||||
};
|
||||
|
||||
template<class R>
|
||||
struct bind_traits<R()> {
|
||||
typedef R(&type)();
|
||||
};
|
||||
|
||||
template<class R, class Arg1>
|
||||
struct bind_traits<R(Arg1)> {
|
||||
typedef R(&type)(Arg1);
|
||||
};
|
||||
|
||||
template<class R, class Arg1, class Arg2>
|
||||
struct bind_traits<R(Arg1, Arg2)> {
|
||||
typedef R(&type)(Arg1, Arg2);
|
||||
};
|
||||
|
||||
template<class R, class Arg1, class Arg2, class Arg3>
|
||||
struct bind_traits<R(Arg1, Arg2, Arg3)> {
|
||||
typedef R(&type)(Arg1, Arg2, Arg3);
|
||||
};
|
||||
|
||||
template<class R, class Arg1, class Arg2, class Arg3, class Arg4>
|
||||
struct bind_traits<R(Arg1, Arg2, Arg3, Arg4)> {
|
||||
typedef R(&type)(Arg1, Arg2, Arg3, Arg4);
|
||||
};
|
||||
|
||||
template<class R, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5>
|
||||
struct bind_traits<R(Arg1, Arg2, Arg3, Arg4, Arg5)> {
|
||||
typedef R(&type)(Arg1, Arg2, Arg3, Arg4, Arg5);
|
||||
};
|
||||
|
||||
template<class R, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6>
|
||||
struct bind_traits<R(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6)> {
|
||||
typedef R(&type)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6);
|
||||
};
|
||||
|
||||
template<class R, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7>
|
||||
struct bind_traits<R(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7)> {
|
||||
typedef R(&type)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7);
|
||||
};
|
||||
|
||||
template<class R, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Arg8>
|
||||
struct bind_traits<R(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8)> {
|
||||
typedef R(&type)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8);
|
||||
};
|
||||
|
||||
template<class R, class Arg1, class Arg2, class Arg3, class Arg4, class Arg5, class Arg6, class Arg7, class Arg8, class Arg9>
|
||||
struct bind_traits<R(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8, Arg9)> {
|
||||
typedef R(&type)(Arg1, Arg2, Arg3, Arg4, Arg5, Arg6, Arg7, Arg8, Arg9);
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct bind_traits<reference_wrapper<T> >{
|
||||
typedef T& type;
|
||||
};
|
||||
|
||||
template<class T>
|
||||
struct bind_traits<const reference_wrapper<T> >{
|
||||
typedef T& type;
|
||||
};
|
||||
|
||||
template<>
|
||||
struct bind_traits<void> {
|
||||
typedef void type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
template <
|
||||
class T0 = null_type, class T1 = null_type, class T2 = null_type,
|
||||
class T3 = null_type, class T4 = null_type, class T5 = null_type,
|
||||
class T6 = null_type, class T7 = null_type, class T8 = null_type,
|
||||
class T9 = null_type
|
||||
>
|
||||
struct bind_tuple_mapper {
|
||||
typedef
|
||||
tuple<typename bind_traits<T0>::type,
|
||||
typename bind_traits<T1>::type,
|
||||
typename bind_traits<T2>::type,
|
||||
typename bind_traits<T3>::type,
|
||||
typename bind_traits<T4>::type,
|
||||
typename bind_traits<T5>::type,
|
||||
typename bind_traits<T6>::type,
|
||||
typename bind_traits<T7>::type,
|
||||
typename bind_traits<T8>::type,
|
||||
typename bind_traits<T9>::type> type;
|
||||
};
|
||||
|
||||
// bind_traits, except map const T& -> const T
|
||||
// this is needed e.g. in currying. Const reference arguments can
|
||||
// refer to temporaries, so it is not safe to store them as references.
|
||||
template <class T> struct remove_const_reference {
|
||||
typedef typename bind_traits<T>::type type;
|
||||
};
|
||||
|
||||
template <class T> struct remove_const_reference<const T&> {
|
||||
typedef const T type;
|
||||
};
|
||||
|
||||
|
||||
// maps the bind argument types to the resulting lambda functor type
|
||||
template <
|
||||
class T0 = null_type, class T1 = null_type, class T2 = null_type,
|
||||
class T3 = null_type, class T4 = null_type, class T5 = null_type,
|
||||
class T6 = null_type, class T7 = null_type, class T8 = null_type,
|
||||
class T9 = null_type
|
||||
>
|
||||
class bind_type_generator {
|
||||
|
||||
typedef typename
|
||||
detail::bind_tuple_mapper<
|
||||
T0, T1, T2, T3, T4, T5, T6, T7, T8, T9
|
||||
>::type args_t;
|
||||
|
||||
BOOST_STATIC_CONSTANT(int, nof_elems = boost::tuples::length<args_t>::value);
|
||||
|
||||
typedef
|
||||
action<
|
||||
nof_elems,
|
||||
function_action<nof_elems>
|
||||
> action_type;
|
||||
|
||||
public:
|
||||
typedef
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
action_type,
|
||||
args_t
|
||||
>
|
||||
> type;
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
} // detail
|
||||
|
||||
template <class T> inline const T& make_const(const T& t) { return t; }
|
||||
|
||||
|
||||
} // end of namespace lambda
|
||||
} // end of namespace boost
|
||||
|
||||
|
||||
|
||||
#endif // BOOST_LAMBDA_TRAITS_HPP
|
||||
737
include/boost/lambda/detail/member_ptr.hpp
Normal file
737
include/boost/lambda/detail/member_ptr.hpp
Normal file
@@ -0,0 +1,737 @@
|
||||
// Boost Lambda Library -- member_ptr.hpp ---------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000 Gary Powell (gary.powell@sierra.com)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// --------------------------------------------------------------------------
|
||||
|
||||
#if !defined(BOOST_LAMBDA_MEMBER_PTR_HPP)
|
||||
#define BOOST_LAMBDA_MEMBER_PTR_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
|
||||
class member_pointer_action {};
|
||||
|
||||
|
||||
namespace detail {
|
||||
|
||||
// the boost type_traits member_pointer traits are not enough,
|
||||
// need to know more details.
|
||||
template<class T>
|
||||
struct member_pointer {
|
||||
typedef typename boost::add_reference<T>::type type;
|
||||
typedef detail::unspecified class_type;
|
||||
typedef detail::unspecified qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = false);
|
||||
};
|
||||
|
||||
template<class T, class U>
|
||||
struct member_pointer<T U::*> {
|
||||
typedef typename boost::add_reference<T>::type type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = true);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = false);
|
||||
};
|
||||
|
||||
template<class T, class U>
|
||||
struct member_pointer<const T U::*> {
|
||||
typedef typename boost::add_reference<const T>::type type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = true);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = false);
|
||||
};
|
||||
|
||||
template<class T, class U>
|
||||
struct member_pointer<volatile T U::*> {
|
||||
typedef typename boost::add_reference<volatile T>::type type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = true);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = false);
|
||||
};
|
||||
|
||||
template<class T, class U>
|
||||
struct member_pointer<const volatile T U::*> {
|
||||
typedef typename boost::add_reference<const volatile T>::type type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = true);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = false);
|
||||
};
|
||||
|
||||
// -- nonconst member functions --
|
||||
template<class T, class U>
|
||||
struct member_pointer<T (U::*)()> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1>
|
||||
struct member_pointer<T (U::*)(A1)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2>
|
||||
struct member_pointer<T (U::*)(A1, A2)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7, A8)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8, class A9>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7, A8, A9)> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
// -- const member functions --
|
||||
template<class T, class U>
|
||||
struct member_pointer<T (U::*)() const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1>
|
||||
struct member_pointer<T (U::*)(A1) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2>
|
||||
struct member_pointer<T (U::*)(A1, A2) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7, A8) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8, class A9>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7, A8, A9) const> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
// -- volatile --
|
||||
template<class T, class U>
|
||||
struct member_pointer<T (U::*)() volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1>
|
||||
struct member_pointer<T (U::*)(A1) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2>
|
||||
struct member_pointer<T (U::*)(A1, A2) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7, A8) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8, class A9>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7, A8, A9) volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
// -- const volatile
|
||||
template<class T, class U>
|
||||
struct member_pointer<T (U::*)() const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1>
|
||||
struct member_pointer<T (U::*)(A1) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2>
|
||||
struct member_pointer<T (U::*)(A1, A2) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7, A8) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
template<class T, class U, class A1, class A2, class A3, class A4, class A5,
|
||||
class A6, class A7, class A8, class A9>
|
||||
struct member_pointer<T (U::*)(A1, A2, A3, A4, A5, A6, A7, A8, A9) const volatile> {
|
||||
typedef T type;
|
||||
typedef U class_type;
|
||||
typedef const volatile U qualified_class_type;
|
||||
BOOST_STATIC_CONSTANT(bool, is_data_member = false);
|
||||
BOOST_STATIC_CONSTANT(bool, is_function_member = true);
|
||||
};
|
||||
|
||||
} // detail
|
||||
|
||||
namespace detail {
|
||||
|
||||
// this class holds a pointer to a member function and the object.
|
||||
// when called, it just calls the member function with the parameters
|
||||
// provided
|
||||
|
||||
// It would have been possible to use existing lambda_functors to represent
|
||||
// a bound member function like this, but to have a separate template is
|
||||
// safer, since now this functor doesn't mix and match with lambda_functors
|
||||
// only thing you can do with this is to call it
|
||||
|
||||
// note that previously instantiated classes
|
||||
// (other_action<member_pointer_action> and member_pointer_action_helper
|
||||
// guarantee, that A and B are
|
||||
// such types, that for objects a and b of corresponding types, a->*b leads
|
||||
// to the builtin ->* to be called. So types that would end in a call to
|
||||
// a user defined ->* do not create a member_pointer_caller object.
|
||||
|
||||
template<class RET, class A, class B>
|
||||
class member_pointer_caller {
|
||||
A a; B b;
|
||||
|
||||
public:
|
||||
member_pointer_caller(const A& aa, const B& bb) : a(aa), b(bb) {}
|
||||
|
||||
RET operator()() const { return (a->*b)(); }
|
||||
|
||||
template<class A1>
|
||||
RET operator()(const A1& a1) const { return (a->*b)(a1); }
|
||||
|
||||
template<class A1, class A2>
|
||||
RET operator()(const A1& a1, const A2& a2) const { return (a->*b)(a1, a2); }
|
||||
|
||||
template<class A1, class A2, class A3>
|
||||
RET operator()(const A1& a1, const A2& a2, const A3& a3) const {
|
||||
return (a->*b)(a1, a2, a3);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4>
|
||||
RET operator()(const A1& a1, const A2& a2, const A3& a3,
|
||||
const A4& a4) const {
|
||||
return (a->*b)(a1, a2, a3, a4);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5>
|
||||
RET operator()(const A1& a1, const A2& a2, const A3& a3, const A4& a4,
|
||||
const A5& a5) const {
|
||||
return (a->*b)(a1, a2, a3, a4, a5);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
RET operator()(const A1& a1, const A2& a2, const A3& a3, const A4& a4,
|
||||
const A5& a5, const A6& a6) const {
|
||||
return (a->*b)(a1, a2, a3, a4, a5, a6);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6,
|
||||
class A7>
|
||||
RET operator()(const A1& a1, const A2& a2, const A3& a3, const A4& a4,
|
||||
const A5& a5, const A6& a6, const A7& a7) const {
|
||||
return (a->*b)(a1, a2, a3, a4, a5, a6, a7);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6,
|
||||
class A7, class A8>
|
||||
RET operator()(const A1& a1, const A2& a2, const A3& a3, const A4& a4,
|
||||
const A5& a5, const A6& a6, const A7& a7,
|
||||
const A8& a8) const {
|
||||
return (a->*b)(a1, a2, a3, a4, a5, a6, a7, a8);
|
||||
}
|
||||
|
||||
template<class A1, class A2, class A3, class A4, class A5, class A6,
|
||||
class A7, class A8, class A9>
|
||||
RET operator()(const A1& a1, const A2& a2, const A3& a3, const A4& a4,
|
||||
const A5& a5, const A6& a6, const A7& a7,
|
||||
const A8& a8, const A9& a9) const {
|
||||
return (a->*b)(a1, a2, a3, a4, a5, a6, a7, a8, a9);
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
// helper templates for return type deduction and action classes
|
||||
// different cases for data member, function member, neither
|
||||
|
||||
// true-true case
|
||||
template <bool Is_data_member, bool Is_function_member>
|
||||
struct member_pointer_action_helper;
|
||||
// cannot be both, no body provided
|
||||
|
||||
// data member case
|
||||
// this means, that B is a data member and A is a pointer type,
|
||||
// so either built-in ->* should be called, or there is an error
|
||||
template <>
|
||||
struct member_pointer_action_helper<true, false> {
|
||||
public:
|
||||
|
||||
template<class RET, class A, class B>
|
||||
static RET apply(A& a, B& b) {
|
||||
return a->*b;
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
struct return_type {
|
||||
private:
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plainB;
|
||||
|
||||
typedef typename detail::member_pointer<plainB>::type type0;
|
||||
// we remove the reference now, as we may have to add cv:s
|
||||
typedef typename boost::remove_reference<type0>::type type1;
|
||||
|
||||
// A is a reference to pointer
|
||||
// remove the top level cv qualifiers and reference
|
||||
typedef typename
|
||||
detail::remove_reference_and_cv<A>::type non_ref_A;
|
||||
|
||||
// A is a pointer type, so take the type pointed to
|
||||
typedef typename ::boost::remove_pointer<non_ref_A>::type non_pointer_A;
|
||||
|
||||
public:
|
||||
// For non-reference types, we must add const and/or volatile if
|
||||
// the pointer type has these qualifiers
|
||||
// If the member is a reference, these do not have any effect
|
||||
// (cv T == T if T is a reference type)
|
||||
typedef typename detail::IF<
|
||||
::boost::is_const<non_pointer_A>::value,
|
||||
typename ::boost::add_const<type1>::type,
|
||||
type1
|
||||
>::RET type2;
|
||||
typedef typename detail::IF<
|
||||
::boost::is_volatile<non_pointer_A>::value,
|
||||
typename ::boost::add_volatile<type2>::type,
|
||||
type2
|
||||
>::RET type3;
|
||||
// add reference back
|
||||
typedef typename ::boost::add_reference<type3>::type type;
|
||||
};
|
||||
};
|
||||
|
||||
// neither case
|
||||
template <>
|
||||
struct member_pointer_action_helper<false, false> {
|
||||
public:
|
||||
template<class RET, class A, class B>
|
||||
static RET apply(A& a, B& b) {
|
||||
// not a built in member pointer operator, just call ->*
|
||||
return a->*b;
|
||||
}
|
||||
// an overloaded member pointer operators, user should have specified
|
||||
// the return type
|
||||
// At this point we know that there is no matching specialization for
|
||||
// return_type_2, so try return_type_2_plain
|
||||
template<class A, class B>
|
||||
struct return_type {
|
||||
|
||||
typedef typename plain_return_type_2<
|
||||
other_action<member_pointer_action>, A, B
|
||||
>::type type;
|
||||
};
|
||||
|
||||
};
|
||||
|
||||
|
||||
// member pointer function case
|
||||
// This is a built in ->* call for a member function,
|
||||
// the only thing that you can do with that, is to give it some arguments
|
||||
// note, it is guaranteed that A is a pointer type, and thus it cannot
|
||||
// be a call to overloaded ->*
|
||||
template <>
|
||||
struct member_pointer_action_helper<false, true> {
|
||||
public:
|
||||
|
||||
template<class RET, class A, class B>
|
||||
static RET apply(A& a, B& b) {
|
||||
typedef typename ::boost::remove_cv<B>::type plainB;
|
||||
typedef typename detail::member_pointer<plainB>::type ret_t;
|
||||
typedef typename ::boost::remove_cv<A>::type plainA;
|
||||
|
||||
// we always strip cv:s to
|
||||
// make the two routes (calling and type deduction)
|
||||
// to give the same results (and the const does not make any functional
|
||||
// difference)
|
||||
return detail::member_pointer_caller<ret_t, plainA, plainB>(a, b);
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
struct return_type {
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plainB;
|
||||
typedef typename detail::member_pointer<plainB>::type ret_t;
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plainA;
|
||||
|
||||
typedef detail::member_pointer_caller<ret_t, plainA, plainB> type;
|
||||
};
|
||||
};
|
||||
|
||||
} // detail
|
||||
|
||||
template<> class other_action<member_pointer_action> {
|
||||
public:
|
||||
template<class RET, class A, class B>
|
||||
static RET apply(A& a, B& b) {
|
||||
typedef typename
|
||||
::boost::remove_cv<B>::type plainB;
|
||||
|
||||
return detail::member_pointer_action_helper<
|
||||
boost::is_pointer<A>::value &&
|
||||
detail::member_pointer<plainB>::is_data_member,
|
||||
boost::is_pointer<A>::value &&
|
||||
detail::member_pointer<plainB>::is_function_member
|
||||
>::template apply<RET>(a, b);
|
||||
}
|
||||
};
|
||||
|
||||
// return type deduction --
|
||||
|
||||
// If the right argument is a pointer to data member,
|
||||
// and the left argument is of compatible pointer to class type
|
||||
// return type is a reference to the data member type
|
||||
|
||||
// if right argument is a pointer to a member function, and the left
|
||||
// argument is of a compatible type, the return type is a
|
||||
// member_pointer_caller (see above)
|
||||
|
||||
// Otherwise, return type deduction fails. There is either an error,
|
||||
// or the user is trying to call an overloaded ->*
|
||||
// In such a case either ret<> must be used, or a return_type_2 user
|
||||
// defined specialization must be provided
|
||||
|
||||
|
||||
template<class A, class B>
|
||||
struct return_type_2<other_action<member_pointer_action>, A, B> {
|
||||
private:
|
||||
typedef typename
|
||||
detail::remove_reference_and_cv<B>::type plainB;
|
||||
public:
|
||||
typedef typename
|
||||
detail::member_pointer_action_helper<
|
||||
detail::member_pointer<plainB>::is_data_member,
|
||||
detail::member_pointer<plainB>::is_function_member
|
||||
>::template return_type<A, B>::type type;
|
||||
};
|
||||
|
||||
// this is the way the generic lambda_functor_base functions instantiate
|
||||
// return type deduction. We turn it into return_type_2, so that the
|
||||
// user can provide specializations on that level.
|
||||
template<class Args>
|
||||
struct return_type_N<other_action<member_pointer_action>, Args> {
|
||||
typedef typename boost::tuples::element<0, Args>::type A;
|
||||
typedef typename boost::tuples::element<1, Args>::type B;
|
||||
typedef typename
|
||||
return_type_2<other_action<member_pointer_action>,
|
||||
typename boost::remove_reference<A>::type,
|
||||
typename boost::remove_reference<B>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
|
||||
template<class Arg1, class Arg2>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<2, other_action<member_pointer_action> >,
|
||||
tuple<lambda_functor<Arg1>, typename const_copy_argument<Arg2>::type>
|
||||
>
|
||||
>
|
||||
operator->*(const lambda_functor<Arg1>& a1, const Arg2& a2)
|
||||
{
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<2, other_action<member_pointer_action> >,
|
||||
tuple<lambda_functor<Arg1>, typename const_copy_argument<Arg2>::type>
|
||||
>
|
||||
(tuple<lambda_functor<Arg1>,
|
||||
typename const_copy_argument<Arg2>::type>(a1, a2));
|
||||
}
|
||||
|
||||
template<class Arg1, class Arg2>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<2, other_action<member_pointer_action> >,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >
|
||||
>
|
||||
>
|
||||
operator->*(const lambda_functor<Arg1>& a1, const lambda_functor<Arg2>& a2)
|
||||
{
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<2, other_action<member_pointer_action> >,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >
|
||||
>
|
||||
(tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >(a1, a2));
|
||||
}
|
||||
|
||||
template<class Arg1, class Arg2>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<2, other_action<member_pointer_action> >,
|
||||
tuple<typename const_copy_argument<Arg1>::type, lambda_functor<Arg2> >
|
||||
>
|
||||
>
|
||||
operator->*(const Arg1& a1, const lambda_functor<Arg2>& a2)
|
||||
{
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<2, other_action<member_pointer_action> >,
|
||||
tuple<typename const_copy_argument<Arg1>::type, lambda_functor<Arg2> >
|
||||
>
|
||||
(tuple<typename const_copy_argument<Arg1>::type,
|
||||
lambda_functor<Arg2> >(a1, a2));
|
||||
}
|
||||
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
139
include/boost/lambda/detail/operator_actions.hpp
Normal file
139
include/boost/lambda/detail/operator_actions.hpp
Normal file
@@ -0,0 +1,139 @@
|
||||
// -- operator_actions.hpp - Boost Lambda Library ----------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
|
||||
// For more information, see http://lambda.cs.utu.fi
|
||||
|
||||
#ifndef BOOST_LAMBDA_OPERATOR_ACTIONS_HPP
|
||||
#define BOOST_LAMBDA_OPERATOR_ACTIONS_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
|
||||
// -- artihmetic ----------------------
|
||||
|
||||
class plus_action {};
|
||||
class minus_action {};
|
||||
class multiply_action {};
|
||||
class divide_action {};
|
||||
class remainder_action {};
|
||||
|
||||
// -- bitwise -------------------
|
||||
|
||||
class leftshift_action {};
|
||||
class rightshift_action {};
|
||||
class xor_action {};
|
||||
|
||||
|
||||
// -- bitwise/logical -------------------
|
||||
|
||||
class and_action {};
|
||||
class or_action {};
|
||||
class not_action {};
|
||||
|
||||
// -- relational -------------------------
|
||||
|
||||
class less_action {};
|
||||
class greater_action {};
|
||||
class lessorequal_action {};
|
||||
class greaterorequal_action {};
|
||||
class equal_action {};
|
||||
class notequal_action {};
|
||||
|
||||
// -- increment/decrement ------------------------------
|
||||
|
||||
class increment_action {};
|
||||
class decrement_action {};
|
||||
|
||||
// -- void return ------------------------------
|
||||
|
||||
// -- other ------------------------------
|
||||
|
||||
class addressof_action {};
|
||||
// class comma_action {}; // defined in actions.hpp
|
||||
class contentsof_action {};
|
||||
// class member_pointer_action {}; (defined in member_ptr.hpp)
|
||||
|
||||
|
||||
// -- actioun group templates --------------------
|
||||
|
||||
template <class Action> class arithmetic_action;
|
||||
template <class Action> class bitwise_action;
|
||||
template <class Action> class logical_action;
|
||||
template <class Action> class relational_action;
|
||||
template <class Action> class arithmetic_assignment_action;
|
||||
template <class Action> class bitwise_assignment_action;
|
||||
template <class Action> class unary_arithmetic_action;
|
||||
template <class Action> class pre_increment_decrement_action;
|
||||
template <class Action> class post_increment_decrement_action;
|
||||
|
||||
// ---------------------------------------------------------
|
||||
|
||||
// actions, for which the existence of protect is checked in return type
|
||||
// deduction.
|
||||
|
||||
template <class Act> struct is_protectable<arithmetic_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <class Act> struct is_protectable<bitwise_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <class Act> struct is_protectable<logical_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <class Act> struct is_protectable<relational_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <class Act>
|
||||
struct is_protectable<arithmetic_assignment_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <class Act> struct is_protectable<bitwise_assignment_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <class Act> struct is_protectable<unary_arithmetic_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <class Act>
|
||||
struct is_protectable<pre_increment_decrement_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <class Act> struct
|
||||
is_protectable<post_increment_decrement_action<Act> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
|
||||
template <> struct is_protectable<other_action<addressof_action> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template <> struct is_protectable<other_action<contentsof_action> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
|
||||
template<> struct is_protectable<other_action<subscript_action> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
template<> struct is_protectable<other_action<assignment_action> > {
|
||||
BOOST_STATIC_CONSTANT(bool, value = true);
|
||||
};
|
||||
|
||||
// NOTE: comma action is also protectable, but the specialization is
|
||||
// in actions.hpp
|
||||
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
271
include/boost/lambda/detail/operator_lambda_func_base.hpp
Normal file
271
include/boost/lambda/detail/operator_lambda_func_base.hpp
Normal file
@@ -0,0 +1,271 @@
|
||||
// Boost Lambda Library - operator_lambda_func_base.hpp -----------------
|
||||
//
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// ------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_OPERATOR_LAMBDA_FUNC_BASE_HPP
|
||||
#define BOOST_LAMBDA_OPERATOR_LAMBDA_FUNC_BASE_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
|
||||
// These operators cannot be implemented as apply functions of action
|
||||
// templates
|
||||
|
||||
|
||||
// Specialization for comma.
|
||||
template<class Args>
|
||||
class lambda_functor_base<other_action<comma_action>, Args> {
|
||||
public:
|
||||
Args args;
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS),
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
private:
|
||||
typedef typename
|
||||
detail::deduce_argument_types<Args, SigArgs>::type rets_t;
|
||||
public:
|
||||
typedef typename return_type_2_comma< // comma needs special handling
|
||||
typename detail::element_or_null<0, rets_t>::type,
|
||||
typename detail::element_or_null<1, rets_t>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
// helper traits to make the expression shorter, takes binary action
|
||||
// bound argument tuple, open argument tuple and gives the return type
|
||||
|
||||
template<class Action, class Bound, class Open> class binary_rt {
|
||||
private:
|
||||
typedef typename
|
||||
detail::deduce_argument_types<Bound, Open>::type rets_t;
|
||||
public:
|
||||
typedef typename return_type_2_prot<
|
||||
Action,
|
||||
typename detail::element_or_null<0, rets_t>::type,
|
||||
typename detail::element_or_null<1, rets_t>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
|
||||
// same for unary actions
|
||||
template<class Action, class Bound, class Open> class unary_rt {
|
||||
private:
|
||||
typedef typename
|
||||
detail::deduce_argument_types<Bound, Open>::type rets_t;
|
||||
public:
|
||||
typedef typename return_type_1_prot<
|
||||
Action,
|
||||
typename detail::element_or_null<0, rets_t>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
|
||||
} // end detail
|
||||
|
||||
// Specialization for logical and (to preserve shortcircuiting)
|
||||
// this could be done with a macro as the others, code used to be different
|
||||
template<class Args>
|
||||
class lambda_functor_base<logical_action<and_action>, Args> {
|
||||
public:
|
||||
Args args;
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) &&
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
template<class SigArgs> struct sig {
|
||||
typedef typename
|
||||
detail::binary_rt<logical_action<and_action>, Args, SigArgs>::type type;
|
||||
};
|
||||
};
|
||||
|
||||
// Specialization for logical or (to preserve shortcircuiting)
|
||||
// this could be done with a macro as the others, code used to be different
|
||||
template<class Args>
|
||||
class lambda_functor_base<logical_action< or_action>, Args> {
|
||||
public:
|
||||
Args args;
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) ||
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
typedef typename
|
||||
detail::binary_rt<logical_action<or_action>, Args, SigArgs>::type type;
|
||||
};
|
||||
};
|
||||
|
||||
// Specialization for subscript
|
||||
template<class Args>
|
||||
class lambda_functor_base<other_action<subscript_action>, Args> {
|
||||
public:
|
||||
Args args;
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS)
|
||||
[detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS)];
|
||||
}
|
||||
|
||||
template<class SigArgs> struct sig {
|
||||
typedef typename
|
||||
detail::binary_rt<other_action<subscript_action>, Args, SigArgs>::type
|
||||
type;
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
#define BOOST_LAMBDA_BINARY_ACTION(SYMBOL, ACTION_CLASS) \
|
||||
template<class Args> \
|
||||
class lambda_functor_base<ACTION_CLASS, Args> { \
|
||||
public: \
|
||||
Args args; \
|
||||
public: \
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {} \
|
||||
\
|
||||
template<class RET, CALL_TEMPLATE_ARGS> \
|
||||
RET call(CALL_FORMAL_ARGS) const { \
|
||||
return detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) \
|
||||
SYMBOL \
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS); \
|
||||
} \
|
||||
template<class SigArgs> struct sig { \
|
||||
typedef typename \
|
||||
detail::binary_rt<ACTION_CLASS, Args, SigArgs>::type type; \
|
||||
}; \
|
||||
};
|
||||
|
||||
#define BOOST_LAMBDA_PREFIX_UNARY_ACTION(SYMBOL, ACTION_CLASS) \
|
||||
template<class Args> \
|
||||
class lambda_functor_base<ACTION_CLASS, Args> { \
|
||||
public: \
|
||||
Args args; \
|
||||
public: \
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {} \
|
||||
\
|
||||
template<class RET, CALL_TEMPLATE_ARGS> \
|
||||
RET call(CALL_FORMAL_ARGS) const { \
|
||||
return SYMBOL \
|
||||
detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS); \
|
||||
} \
|
||||
template<class SigArgs> struct sig { \
|
||||
typedef typename \
|
||||
detail::unary_rt<ACTION_CLASS, Args, SigArgs>::type type; \
|
||||
}; \
|
||||
};
|
||||
|
||||
#define BOOST_LAMBDA_POSTFIX_UNARY_ACTION(SYMBOL, ACTION_CLASS) \
|
||||
template<class Args> \
|
||||
class lambda_functor_base<ACTION_CLASS, Args> { \
|
||||
public: \
|
||||
Args args; \
|
||||
public: \
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {} \
|
||||
\
|
||||
template<class RET, CALL_TEMPLATE_ARGS> \
|
||||
RET call(CALL_FORMAL_ARGS) const { \
|
||||
return \
|
||||
detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) SYMBOL; \
|
||||
} \
|
||||
template<class SigArgs> struct sig { \
|
||||
typedef typename \
|
||||
detail::unary_rt<ACTION_CLASS, Args, SigArgs>::type type; \
|
||||
}; \
|
||||
};
|
||||
|
||||
BOOST_LAMBDA_BINARY_ACTION(+,arithmetic_action<plus_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(-,arithmetic_action<minus_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(*,arithmetic_action<multiply_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(/,arithmetic_action<divide_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(%,arithmetic_action<remainder_action>)
|
||||
|
||||
BOOST_LAMBDA_BINARY_ACTION(<<,bitwise_action<leftshift_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(>>,bitwise_action<rightshift_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(&,bitwise_action<and_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(|,bitwise_action<or_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(^,bitwise_action<xor_action>)
|
||||
|
||||
BOOST_LAMBDA_BINARY_ACTION(<,relational_action<less_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(>,relational_action<greater_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(<=,relational_action<lessorequal_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(>=,relational_action<greaterorequal_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(==,relational_action<equal_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(!=,relational_action<notequal_action>)
|
||||
|
||||
BOOST_LAMBDA_BINARY_ACTION(+=,arithmetic_assignment_action<plus_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(-=,arithmetic_assignment_action<minus_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(*=,arithmetic_assignment_action<multiply_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(/=,arithmetic_assignment_action<divide_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(%=,arithmetic_assignment_action<remainder_action>)
|
||||
|
||||
BOOST_LAMBDA_BINARY_ACTION(<<=,bitwise_assignment_action<leftshift_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(>>=,bitwise_assignment_action<rightshift_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(&=,bitwise_assignment_action<and_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(|=,bitwise_assignment_action<or_action>)
|
||||
BOOST_LAMBDA_BINARY_ACTION(^=,bitwise_assignment_action<xor_action>)
|
||||
|
||||
BOOST_LAMBDA_BINARY_ACTION(=,other_action< assignment_action>)
|
||||
|
||||
|
||||
BOOST_LAMBDA_PREFIX_UNARY_ACTION(+, unary_arithmetic_action<plus_action>)
|
||||
BOOST_LAMBDA_PREFIX_UNARY_ACTION(-, unary_arithmetic_action<minus_action>)
|
||||
BOOST_LAMBDA_PREFIX_UNARY_ACTION(~, bitwise_action<not_action>)
|
||||
BOOST_LAMBDA_PREFIX_UNARY_ACTION(!, logical_action<not_action>)
|
||||
BOOST_LAMBDA_PREFIX_UNARY_ACTION(++, pre_increment_decrement_action<increment_action>)
|
||||
BOOST_LAMBDA_PREFIX_UNARY_ACTION(--, pre_increment_decrement_action<decrement_action>)
|
||||
|
||||
BOOST_LAMBDA_PREFIX_UNARY_ACTION(&,other_action<addressof_action>)
|
||||
BOOST_LAMBDA_PREFIX_UNARY_ACTION(*,other_action<contentsof_action>)
|
||||
|
||||
BOOST_LAMBDA_POSTFIX_UNARY_ACTION(++, post_increment_decrement_action<increment_action>)
|
||||
BOOST_LAMBDA_POSTFIX_UNARY_ACTION(--, post_increment_decrement_action<decrement_action>)
|
||||
|
||||
|
||||
#undef BOOST_LAMBDA_POSTFIX_UNARY_ACTION
|
||||
#undef BOOST_LAMBDA_PREFIX_UNARY_ACTION
|
||||
#undef BOOST_LAMBDA_BINARY_ACTION
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
892
include/boost/lambda/detail/operator_return_type_traits.hpp
Normal file
892
include/boost/lambda/detail/operator_return_type_traits.hpp
Normal file
@@ -0,0 +1,892 @@
|
||||
// operator_return_type_traits.hpp -- Boost Lambda Library ------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
#ifndef BOOST_LAMBDA_OPERATOR_RETURN_TYPE_TRAITS_HPP
|
||||
#define BOOST_LAMBDA_OPERATOR_RETURN_TYPE_TRAITS_HPP
|
||||
|
||||
#include "boost/lambda/detail/is_instance_of.hpp"
|
||||
#include "boost/type_traits/is_same.hpp"
|
||||
#include "boost/type_traits/is_pointer.hpp"
|
||||
#include "boost/type_traits/is_float.hpp"
|
||||
#include "boost/type_traits/is_convertible.hpp"
|
||||
#include "boost/type_traits/remove_pointer.hpp"
|
||||
#include "boost/type_traits/remove_const.hpp"
|
||||
#include "boost/type_traits/remove_reference.hpp"
|
||||
|
||||
#include "boost/indirect_reference.hpp"
|
||||
#include "boost/detail/container_fwd.hpp"
|
||||
|
||||
#include <cstddef> // needed for the ptrdiff_t
|
||||
#include <iosfwd> // for istream and ostream
|
||||
|
||||
#include <iterator> // needed for operator&
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
namespace detail {
|
||||
|
||||
// -- general helper templates for type deduction ------------------
|
||||
|
||||
// Much of the type deduction code for standard arithmetic types from Gary Powell
|
||||
|
||||
template <class A> struct promote_code { static const int value = -1; };
|
||||
// this means that a code is not defined for A
|
||||
|
||||
// -- the next 5 types are needed in if_then_else_return
|
||||
// the promotion order is not important, but they must have distinct values.
|
||||
template <> struct promote_code<bool> { static const int value = 10; };
|
||||
template <> struct promote_code<char> { static const int value = 20; };
|
||||
template <> struct promote_code<unsigned char> { static const int value = 30; };
|
||||
template <> struct promote_code<signed char> { static const int value = 40; };
|
||||
template <> struct promote_code<short int> { static const int value = 50; };
|
||||
// ----------
|
||||
|
||||
template <> struct promote_code<int> { static const int value = 100; };
|
||||
template <> struct promote_code<unsigned int> { static const int value = 200; };
|
||||
template <> struct promote_code<long> { static const int value = 300; };
|
||||
template <> struct promote_code<unsigned long> { static const int value = 400; };
|
||||
|
||||
template <> struct promote_code<float> { static const int value = 500; };
|
||||
template <> struct promote_code<double> { static const int value = 600; };
|
||||
template <> struct promote_code<long double> { static const int value = 700; };
|
||||
|
||||
// TODO: wchar_t
|
||||
|
||||
// forward delcaration of complex.
|
||||
|
||||
} // namespace detail
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
namespace detail {
|
||||
|
||||
template <> struct promote_code< std::complex<float> > { static const int value = 800; };
|
||||
template <> struct promote_code< std::complex<double> > { static const int value = 900; };
|
||||
template <> struct promote_code< std::complex<long double> > { static const int value = 1000; };
|
||||
|
||||
// -- int promotion -------------------------------------------
|
||||
template <class T> struct promote_to_int { typedef T type; };
|
||||
|
||||
template <> struct promote_to_int<bool> { typedef int type; };
|
||||
template <> struct promote_to_int<char> { typedef int type; };
|
||||
template <> struct promote_to_int<unsigned char> { typedef int type; };
|
||||
template <> struct promote_to_int<signed char> { typedef int type; };
|
||||
template <> struct promote_to_int<short int> { typedef int type; };
|
||||
|
||||
// The unsigned short int promotion rule is this:
|
||||
// unsigned short int to signed int if a signed int can hold all values
|
||||
// of unsigned short int, otherwise go to unsigned int.
|
||||
template <> struct promote_to_int<unsigned short int>
|
||||
{
|
||||
typedef
|
||||
detail::IF<sizeof(int) <= sizeof(unsigned short int),
|
||||
// I had the logic reversed but ">" messes up the parsing.
|
||||
unsigned int,
|
||||
int>::RET type;
|
||||
};
|
||||
|
||||
|
||||
// TODO: think, should there be default behaviour for non-standard types?
|
||||
|
||||
} // namespace detail
|
||||
|
||||
// ------------------------------------------
|
||||
// Unary actions ----------------------------
|
||||
// ------------------------------------------
|
||||
|
||||
template<class Act, class A>
|
||||
struct plain_return_type_1 {
|
||||
typedef detail::unspecified type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
template<class Act, class A>
|
||||
struct plain_return_type_1<unary_arithmetic_action<Act>, A> {
|
||||
typedef A type;
|
||||
};
|
||||
|
||||
template<class Act, class A>
|
||||
struct return_type_1<unary_arithmetic_action<Act>, A> {
|
||||
typedef
|
||||
typename plain_return_type_1<
|
||||
unary_arithmetic_action<Act>,
|
||||
typename detail::remove_reference_and_cv<A>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
|
||||
template<class A>
|
||||
struct plain_return_type_1<bitwise_action<not_action>, A> {
|
||||
typedef A type;
|
||||
};
|
||||
|
||||
// bitwise not, operator~()
|
||||
template<class A> struct return_type_1<bitwise_action<not_action>, A> {
|
||||
typedef
|
||||
typename plain_return_type_1<
|
||||
bitwise_action<not_action>,
|
||||
typename detail::remove_reference_and_cv<A>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
|
||||
// prefix increment and decrement operators return
|
||||
// their argument by default as a non-const reference
|
||||
template<class Act, class A>
|
||||
struct plain_return_type_1<pre_increment_decrement_action<Act>, A> {
|
||||
typedef A& type;
|
||||
};
|
||||
|
||||
template<class Act, class A>
|
||||
struct return_type_1<pre_increment_decrement_action<Act>, A> {
|
||||
typedef
|
||||
typename plain_return_type_1<
|
||||
pre_increment_decrement_action<Act>,
|
||||
typename detail::remove_reference_and_cv<A>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// post decrement just returns the same plain type.
|
||||
template<class Act, class A>
|
||||
struct plain_return_type_1<post_increment_decrement_action<Act>, A> {
|
||||
typedef A type;
|
||||
};
|
||||
|
||||
template<class Act, class A>
|
||||
struct return_type_1<post_increment_decrement_action<Act>, A>
|
||||
{
|
||||
typedef
|
||||
typename plain_return_type_1<
|
||||
post_increment_decrement_action<Act>,
|
||||
typename detail::remove_reference_and_cv<A>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// logical not, operator!()
|
||||
template<class A>
|
||||
struct plain_return_type_1<logical_action<not_action>, A> {
|
||||
typedef bool type;
|
||||
};
|
||||
|
||||
template<class A>
|
||||
struct return_type_1<logical_action<not_action>, A> {
|
||||
typedef
|
||||
typename plain_return_type_1<
|
||||
logical_action<not_action>,
|
||||
typename detail::remove_reference_and_cv<A>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// address of action ---------------------------------------
|
||||
|
||||
|
||||
template<class A>
|
||||
struct return_type_1<other_action<addressof_action>, A> {
|
||||
typedef
|
||||
typename plain_return_type_1<
|
||||
other_action<addressof_action>,
|
||||
typename detail::remove_reference_and_cv<A>::type
|
||||
>::type type1;
|
||||
|
||||
// If no user defined specialization for A, then return the
|
||||
// cv qualified pointer to A
|
||||
typedef typename detail::IF<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
typename boost::remove_reference<A>::type*,
|
||||
type1
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
// contentsof action ------------------------------------
|
||||
|
||||
// TODO: this deduction may lead to fail directly,
|
||||
// (if A has no specialization for iterator_traits and has no
|
||||
// typedef A::reference.
|
||||
// There is no easy way around this, cause there doesn't seem to be a way
|
||||
// to test whether a class is an iterator or not.
|
||||
|
||||
// The default works with std::iterators.
|
||||
|
||||
namespace detail {
|
||||
|
||||
// A is a nonreference type
|
||||
template <class A> struct contentsof_type {
|
||||
typedef typename boost::indirect_reference<A>::type type;
|
||||
};
|
||||
|
||||
// this is since the nullary () in lambda_functor is always instantiated
|
||||
template <> struct contentsof_type<null_type> {
|
||||
typedef detail::unspecified type;
|
||||
};
|
||||
|
||||
|
||||
template <class A> struct contentsof_type<const A> {
|
||||
typedef typename contentsof_type<A>::type type;
|
||||
};
|
||||
|
||||
template <class A> struct contentsof_type<volatile A> {
|
||||
typedef typename contentsof_type<A>::type type;
|
||||
};
|
||||
|
||||
template <class A> struct contentsof_type<const volatile A> {
|
||||
typedef typename contentsof_type<A>::type type;
|
||||
};
|
||||
|
||||
// standard iterator traits should take care of the pointer types
|
||||
// but just to be on the safe side, we have the specializations here:
|
||||
// these work even if A is cv-qualified.
|
||||
template <class A> struct contentsof_type<A*> {
|
||||
typedef A& type;
|
||||
};
|
||||
template <class A> struct contentsof_type<A* const> {
|
||||
typedef A& type;
|
||||
};
|
||||
template <class A> struct contentsof_type<A* volatile> {
|
||||
typedef A& type;
|
||||
};
|
||||
template <class A> struct contentsof_type<A* const volatile> {
|
||||
typedef A& type;
|
||||
};
|
||||
|
||||
template<class A, int N> struct contentsof_type<A[N]> {
|
||||
typedef A& type;
|
||||
};
|
||||
template<class A, int N> struct contentsof_type<const A[N]> {
|
||||
typedef const A& type;
|
||||
};
|
||||
template<class A, int N> struct contentsof_type<volatile A[N]> {
|
||||
typedef volatile A& type;
|
||||
};
|
||||
template<class A, int N> struct contentsof_type<const volatile A[N]> {
|
||||
typedef const volatile A& type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
} // end detail
|
||||
|
||||
template<class A>
|
||||
struct return_type_1<other_action<contentsof_action>, A> {
|
||||
|
||||
typedef
|
||||
typename plain_return_type_1<
|
||||
other_action<contentsof_action>,
|
||||
typename detail::remove_reference_and_cv<A>::type
|
||||
>::type type1;
|
||||
|
||||
// If no user defined specialization for A, then return the
|
||||
// cv qualified pointer to A
|
||||
typedef typename
|
||||
detail::IF_type<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
detail::contentsof_type<
|
||||
typename boost::remove_reference<A>::type
|
||||
>,
|
||||
detail::identity_mapping<type1>
|
||||
>::type type;
|
||||
};
|
||||
|
||||
|
||||
// ------------------------------------------------------------------
|
||||
// binary actions ---------------------------------------------------
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
// here the default case is: no user defined versions:
|
||||
template <class Act, class A, class B>
|
||||
struct plain_return_type_2 {
|
||||
typedef detail::unspecified type;
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
// error classes
|
||||
class illegal_pointer_arithmetic{};
|
||||
|
||||
// pointer arithmetic type deductions ----------------------
|
||||
// value = false means that this is not a pointer arithmetic case
|
||||
// value = true means, that this can be a pointer arithmetic case, but not necessarily is
|
||||
// This means, that for user defined operators for pointer types, say for some operator+(X, *Y),
|
||||
// the deductions must be coded at an earliel level (return_type_2).
|
||||
|
||||
template<class Act, class A, class B>
|
||||
struct pointer_arithmetic_traits { static const bool value = false; };
|
||||
|
||||
template<class A, class B>
|
||||
struct pointer_arithmetic_traits<plus_action, A, B> {
|
||||
|
||||
typedef typename
|
||||
array_to_pointer<typename boost::remove_reference<A>::type>::type AP;
|
||||
typedef typename
|
||||
array_to_pointer<typename boost::remove_reference<B>::type>::type BP;
|
||||
|
||||
static const bool is_pointer_A = boost::is_pointer<AP>::value;
|
||||
static const bool is_pointer_B = boost::is_pointer<BP>::value;
|
||||
|
||||
static const bool value = is_pointer_A || is_pointer_B;
|
||||
|
||||
// can't add two pointers.
|
||||
// note, that we do not check wether the other type is valid for
|
||||
// addition with a pointer.
|
||||
// the compiler will catch it in the apply function
|
||||
|
||||
typedef typename
|
||||
detail::IF<
|
||||
is_pointer_A && is_pointer_B,
|
||||
detail::return_type_deduction_failure<
|
||||
detail::illegal_pointer_arithmetic
|
||||
>,
|
||||
typename detail::IF<is_pointer_A, AP, BP>::RET
|
||||
>::RET type;
|
||||
|
||||
};
|
||||
|
||||
template<class A, class B>
|
||||
struct pointer_arithmetic_traits<minus_action, A, B> {
|
||||
typedef typename
|
||||
array_to_pointer<typename boost::remove_reference<A>::type>::type AP;
|
||||
typedef typename
|
||||
array_to_pointer<typename boost::remove_reference<B>::type>::type BP;
|
||||
|
||||
static const bool is_pointer_A = boost::is_pointer<AP>::value;
|
||||
static const bool is_pointer_B = boost::is_pointer<BP>::value;
|
||||
|
||||
static const bool value = is_pointer_A || is_pointer_B;
|
||||
|
||||
static const bool same_pointer_type =
|
||||
is_pointer_A && is_pointer_B &&
|
||||
boost::is_same<
|
||||
typename boost::remove_const<
|
||||
typename boost::remove_pointer<
|
||||
typename boost::remove_const<AP>::type
|
||||
>::type
|
||||
>::type,
|
||||
typename boost::remove_const<
|
||||
typename boost::remove_pointer<
|
||||
typename boost::remove_const<BP>::type
|
||||
>::type
|
||||
>::type
|
||||
>::value;
|
||||
|
||||
// ptr - ptr has type ptrdiff_t
|
||||
// note, that we do not check if, in ptr - B, B is
|
||||
// valid for subtraction with a pointer.
|
||||
// the compiler will catch it in the apply function
|
||||
|
||||
typedef typename
|
||||
detail::IF<
|
||||
same_pointer_type, const std::ptrdiff_t,
|
||||
typename detail::IF<
|
||||
is_pointer_A,
|
||||
AP,
|
||||
detail::return_type_deduction_failure<detail::illegal_pointer_arithmetic>
|
||||
>::RET
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
// -- arithmetic actions ---------------------------------------------
|
||||
|
||||
namespace detail {
|
||||
|
||||
template<bool is_pointer_arithmetic, class Act, class A, class B>
|
||||
struct return_type_2_arithmetic_phase_1;
|
||||
|
||||
template<class A, class B> struct return_type_2_arithmetic_phase_2;
|
||||
template<class A, class B> struct return_type_2_arithmetic_phase_3;
|
||||
|
||||
} // namespace detail
|
||||
|
||||
|
||||
// drop any qualifiers from the argument types within arithmetic_action
|
||||
template<class A, class B, class Act>
|
||||
struct return_type_2<arithmetic_action<Act>, A, B>
|
||||
{
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<arithmetic_action<Act>, plain_A, plain_B>::type type1;
|
||||
|
||||
// if user defined return type, do not enter the whole arithmetic deductions
|
||||
typedef typename
|
||||
detail::IF_type<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
detail::return_type_2_arithmetic_phase_1<
|
||||
detail::pointer_arithmetic_traits<Act, A, B>::value, Act, A, B
|
||||
>,
|
||||
plain_return_type_2<arithmetic_action<Act>, plain_A, plain_B>
|
||||
>::type type;
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
// perform integral promotion, no pointer arithmetic
|
||||
template<bool is_pointer_arithmetic, class Act, class A, class B>
|
||||
struct return_type_2_arithmetic_phase_1
|
||||
{
|
||||
typedef typename
|
||||
return_type_2_arithmetic_phase_2<
|
||||
typename remove_reference_and_cv<A>::type,
|
||||
typename remove_reference_and_cv<B>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// pointer_arithmetic
|
||||
template<class Act, class A, class B>
|
||||
struct return_type_2_arithmetic_phase_1<true, Act, A, B>
|
||||
{
|
||||
typedef typename
|
||||
pointer_arithmetic_traits<Act, A, B>::type type;
|
||||
};
|
||||
|
||||
template<class A, class B>
|
||||
struct return_type_2_arithmetic_phase_2 {
|
||||
typedef typename
|
||||
return_type_2_arithmetic_phase_3<
|
||||
typename promote_to_int<A>::type,
|
||||
typename promote_to_int<B>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// specialization for unsigned int.
|
||||
// We only have to do these two specialization because the value promotion will
|
||||
// take care of the other cases.
|
||||
// The unsigned int promotion rule is this:
|
||||
// unsigned int to long if a long can hold all values of unsigned int,
|
||||
// otherwise go to unsigned long.
|
||||
|
||||
// struct so I don't have to type this twice.
|
||||
struct promotion_of_unsigned_int
|
||||
{
|
||||
typedef
|
||||
detail::IF<sizeof(long) <= sizeof(unsigned int),
|
||||
unsigned long,
|
||||
long>::RET type;
|
||||
};
|
||||
|
||||
template<>
|
||||
struct return_type_2_arithmetic_phase_2<unsigned int, long>
|
||||
{
|
||||
typedef promotion_of_unsigned_int::type type;
|
||||
};
|
||||
template<>
|
||||
struct return_type_2_arithmetic_phase_2<long, unsigned int>
|
||||
{
|
||||
typedef promotion_of_unsigned_int::type type;
|
||||
};
|
||||
|
||||
|
||||
template<class A, class B> struct return_type_2_arithmetic_phase_3 {
|
||||
enum { promote_code_A_value = promote_code<A>::value,
|
||||
promote_code_B_value = promote_code<B>::value }; // enums for KCC
|
||||
typedef typename
|
||||
detail::IF<
|
||||
promote_code_A_value == -1 || promote_code_B_value == -1,
|
||||
detail::return_type_deduction_failure<return_type_2_arithmetic_phase_3>,
|
||||
typename detail::IF<
|
||||
((int)promote_code_A_value > (int)promote_code_B_value),
|
||||
A,
|
||||
B
|
||||
>::RET
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
// -- bitwise actions -------------------------------------------
|
||||
// note: for integral types deuduction is similar to arithmetic actions.
|
||||
|
||||
// drop any qualifiers from the argument types within arithmetic action
|
||||
template<class A, class B, class Act>
|
||||
struct return_type_2<bitwise_action<Act>, A, B>
|
||||
{
|
||||
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<bitwise_action<Act>, plain_A, plain_B>::type type1;
|
||||
|
||||
// if user defined return type, do not enter type deductions
|
||||
typedef typename
|
||||
detail::IF_type<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
return_type_2<arithmetic_action<plus_action>, A, B>,
|
||||
plain_return_type_2<bitwise_action<Act>, plain_A, plain_B>
|
||||
>::type type;
|
||||
|
||||
// plus_action is just a random pick, has to be a concrete instance
|
||||
|
||||
// TODO: This check is only valid for built-in types, overloaded types might
|
||||
// accept floating point operators
|
||||
|
||||
// bitwise operators not defined for floating point types
|
||||
// these test are not strictly needed here, since the error will be caught in
|
||||
// the apply function
|
||||
BOOST_STATIC_ASSERT(!(boost::is_float<plain_A>::value && boost::is_float<plain_B>::value));
|
||||
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
|
||||
|
||||
template <class T> struct get_ostream_type {
|
||||
typedef std::basic_ostream<typename T::char_type,
|
||||
typename T::traits_type>& type;
|
||||
};
|
||||
|
||||
template <class T> struct get_istream_type {
|
||||
typedef std::basic_istream<typename T::char_type,
|
||||
typename T::traits_type>& type;
|
||||
};
|
||||
|
||||
template<class A, class B>
|
||||
struct leftshift_type {
|
||||
private:
|
||||
typedef typename boost::remove_reference<A>::type plainA;
|
||||
public:
|
||||
typedef typename detail::IF_type<
|
||||
is_instance_of_2<plainA, std::basic_ostream>::value,
|
||||
get_ostream_type<plainA>, //reference to the stream
|
||||
detail::remove_reference_and_cv<A>
|
||||
>::type type;
|
||||
};
|
||||
|
||||
template<class A, class B>
|
||||
struct rightshift_type {
|
||||
private:
|
||||
typedef typename boost::remove_reference<A>::type plainA;
|
||||
public:
|
||||
typedef typename detail::IF_type<
|
||||
is_instance_of_2<plainA, std::basic_istream>::value,
|
||||
get_istream_type<plainA>, //reference to the stream
|
||||
detail::remove_reference_and_cv<A>
|
||||
>::type type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
} // end detail
|
||||
|
||||
// ostream
|
||||
template<class A, class B>
|
||||
struct return_type_2<bitwise_action<leftshift_action>, A, B>
|
||||
{
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<bitwise_action<leftshift_action>, plain_A, plain_B>::type type1;
|
||||
|
||||
// if user defined return type, do not enter type deductions
|
||||
typedef typename
|
||||
detail::IF_type<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
detail::leftshift_type<A, B>,
|
||||
plain_return_type_2<bitwise_action<leftshift_action>, plain_A, plain_B>
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// istream
|
||||
template<class A, class B>
|
||||
struct return_type_2<bitwise_action<rightshift_action>, A, B>
|
||||
{
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<bitwise_action<rightshift_action>, plain_A, plain_B>::type type1;
|
||||
|
||||
// if user defined return type, do not enter type deductions
|
||||
typedef typename
|
||||
detail::IF_type<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
detail::rightshift_type<A, B>,
|
||||
plain_return_type_2<bitwise_action<rightshift_action>, plain_A, plain_B>
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// -- logical actions ----------------------------------------
|
||||
// always bool
|
||||
// NOTE: this may not be true for some weird user-defined types,
|
||||
template<class A, class B, class Act>
|
||||
struct plain_return_type_2<logical_action<Act>, A, B> {
|
||||
typedef bool type;
|
||||
};
|
||||
|
||||
template<class A, class B, class Act>
|
||||
struct return_type_2<logical_action<Act>, A, B> {
|
||||
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<logical_action<Act>, plain_A, plain_B>::type type;
|
||||
|
||||
};
|
||||
|
||||
|
||||
// -- relational actions ----------------------------------------
|
||||
// always bool
|
||||
// NOTE: this may not be true for some weird user-defined types,
|
||||
template<class A, class B, class Act>
|
||||
struct plain_return_type_2<relational_action<Act>, A, B> {
|
||||
typedef bool type;
|
||||
};
|
||||
|
||||
template<class A, class B, class Act>
|
||||
struct return_type_2<relational_action<Act>, A, B> {
|
||||
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<relational_action<Act>, plain_A, plain_B>::type type;
|
||||
};
|
||||
|
||||
// Assingment actions -----------------------------------------------
|
||||
// return type is the type of the first argument as reference
|
||||
|
||||
// note that cv-qualifiers are preserved.
|
||||
// Yes, assignment operator can be const!
|
||||
|
||||
// NOTE: this may not be true for some weird user-defined types,
|
||||
|
||||
template<class A, class B, class Act>
|
||||
struct return_type_2<arithmetic_assignment_action<Act>, A, B> {
|
||||
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<
|
||||
arithmetic_assignment_action<Act>, plain_A, plain_B
|
||||
>::type type1;
|
||||
|
||||
typedef typename
|
||||
detail::IF<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
typename boost::add_reference<A>::type,
|
||||
type1
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
template<class A, class B, class Act>
|
||||
struct return_type_2<bitwise_assignment_action<Act>, A, B> {
|
||||
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<
|
||||
bitwise_assignment_action<Act>, plain_A, plain_B
|
||||
>::type type1;
|
||||
|
||||
typedef typename
|
||||
detail::IF<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
typename boost::add_reference<A>::type,
|
||||
type1
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
template<class A, class B>
|
||||
struct return_type_2<other_action<assignment_action>, A, B> {
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<
|
||||
other_action<assignment_action>, plain_A, plain_B
|
||||
>::type type1;
|
||||
|
||||
typedef typename
|
||||
detail::IF<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
typename boost::add_reference<A>::type,
|
||||
type1
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
// -- other actions ----------------------------------------
|
||||
|
||||
// comma action ----------------------------------
|
||||
// Note: this may not be true for some weird user-defined types,
|
||||
|
||||
// NOTE! This only tries the plain_return_type_2 layer and gives
|
||||
// detail::unspecified as default. If no such specialization is found, the
|
||||
// type rule in the spcecialization of the return_type_2_prot is used
|
||||
// to give the type of the right argument (which can be a reference too)
|
||||
// (The built in operator, can return a l- or rvalue).
|
||||
template<class A, class B>
|
||||
struct return_type_2<other_action<comma_action>, A, B> {
|
||||
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<
|
||||
other_action<comma_action>, plain_A, plain_B
|
||||
>::type type;
|
||||
};
|
||||
|
||||
// subscript action -----------------------------------------------
|
||||
|
||||
|
||||
namespace detail {
|
||||
// A and B are nonreference types
|
||||
template <class A, class B> struct subscript_type {
|
||||
typedef detail::unspecified type;
|
||||
};
|
||||
|
||||
template <class A, class B> struct subscript_type<A*, B> {
|
||||
typedef A& type;
|
||||
};
|
||||
template <class A, class B> struct subscript_type<A* const, B> {
|
||||
typedef A& type;
|
||||
};
|
||||
template <class A, class B> struct subscript_type<A* volatile, B> {
|
||||
typedef A& type;
|
||||
};
|
||||
template <class A, class B> struct subscript_type<A* const volatile, B> {
|
||||
typedef A& type;
|
||||
};
|
||||
|
||||
|
||||
template<class A, class B, int N> struct subscript_type<A[N], B> {
|
||||
typedef A& type;
|
||||
};
|
||||
|
||||
// these 3 specializations are needed to make gcc <3 happy
|
||||
template<class A, class B, int N> struct subscript_type<const A[N], B> {
|
||||
typedef const A& type;
|
||||
};
|
||||
template<class A, class B, int N> struct subscript_type<volatile A[N], B> {
|
||||
typedef volatile A& type;
|
||||
};
|
||||
template<class A, class B, int N> struct subscript_type<const volatile A[N], B> {
|
||||
typedef const volatile A& type;
|
||||
};
|
||||
|
||||
} // end detail
|
||||
|
||||
template<class A, class B>
|
||||
struct return_type_2<other_action<subscript_action>, A, B> {
|
||||
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plain_A;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plain_B;
|
||||
|
||||
typedef typename boost::remove_reference<A>::type nonref_A;
|
||||
typedef typename boost::remove_reference<B>::type nonref_B;
|
||||
|
||||
typedef typename
|
||||
plain_return_type_2<
|
||||
other_action<subscript_action>, plain_A, plain_B
|
||||
>::type type1;
|
||||
|
||||
typedef typename
|
||||
detail::IF_type<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
detail::subscript_type<nonref_A, nonref_B>,
|
||||
plain_return_type_2<other_action<subscript_action>, plain_A, plain_B>
|
||||
>::type type;
|
||||
|
||||
};
|
||||
|
||||
template<class Key, class T, class Cmp, class Allocator, class B>
|
||||
struct plain_return_type_2<other_action<subscript_action>, std::map<Key, T, Cmp, Allocator>, B> {
|
||||
typedef T& type;
|
||||
// T == std::map<Key, T, Cmp, Allocator>::mapped_type;
|
||||
};
|
||||
|
||||
template<class Key, class T, class Cmp, class Allocator, class B>
|
||||
struct plain_return_type_2<other_action<subscript_action>, std::multimap<Key, T, Cmp, Allocator>, B> {
|
||||
typedef T& type;
|
||||
// T == std::map<Key, T, Cmp, Allocator>::mapped_type;
|
||||
};
|
||||
|
||||
// deque
|
||||
template<class T, class Allocator, class B>
|
||||
struct plain_return_type_2<other_action<subscript_action>, std::deque<T, Allocator>, B> {
|
||||
typedef typename std::deque<T, Allocator>::reference type;
|
||||
};
|
||||
template<class T, class Allocator, class B>
|
||||
struct plain_return_type_2<other_action<subscript_action>, const std::deque<T, Allocator>, B> {
|
||||
typedef typename std::deque<T, Allocator>::const_reference type;
|
||||
};
|
||||
|
||||
// vector
|
||||
template<class T, class Allocator, class B>
|
||||
struct plain_return_type_2<other_action<subscript_action>, std::vector<T, Allocator>, B> {
|
||||
typedef typename std::vector<T, Allocator>::reference type;
|
||||
};
|
||||
template<class T, class Allocator, class B>
|
||||
struct plain_return_type_2<other_action<subscript_action>, const std::vector<T, Allocator>, B> {
|
||||
typedef typename std::vector<T, Allocator>::const_reference type;
|
||||
};
|
||||
|
||||
// basic_string
|
||||
template<class Char, class Traits, class Allocator, class B>
|
||||
struct plain_return_type_2<other_action<subscript_action>, std::basic_string<Char, Traits, Allocator>, B> {
|
||||
typedef typename std::basic_string<Char, Traits, Allocator>::reference type;
|
||||
};
|
||||
template<class Char, class Traits, class Allocator, class B>
|
||||
struct plain_return_type_2<other_action<subscript_action>, const std::basic_string<Char, Traits, Allocator>, B> {
|
||||
typedef typename std::basic_string<Char, Traits, Allocator>::const_reference type;
|
||||
};
|
||||
|
||||
template<class Char, class Traits, class Allocator>
|
||||
struct plain_return_type_2<arithmetic_action<plus_action>,
|
||||
std::basic_string<Char, Traits, Allocator>,
|
||||
std::basic_string<Char, Traits, Allocator> > {
|
||||
typedef std::basic_string<Char, Traits, Allocator> type;
|
||||
};
|
||||
|
||||
template<class Char, class Traits, class Allocator>
|
||||
struct plain_return_type_2<arithmetic_action<plus_action>,
|
||||
const Char*,
|
||||
std::basic_string<Char, Traits, Allocator> > {
|
||||
typedef std::basic_string<Char, Traits, Allocator> type;
|
||||
};
|
||||
|
||||
template<class Char, class Traits, class Allocator>
|
||||
struct plain_return_type_2<arithmetic_action<plus_action>,
|
||||
std::basic_string<Char, Traits, Allocator>,
|
||||
const Char*> {
|
||||
typedef std::basic_string<Char, Traits, Allocator> type;
|
||||
};
|
||||
|
||||
template<class Char, class Traits, class Allocator, std::size_t N>
|
||||
struct plain_return_type_2<arithmetic_action<plus_action>,
|
||||
Char[N],
|
||||
std::basic_string<Char, Traits, Allocator> > {
|
||||
typedef std::basic_string<Char, Traits, Allocator> type;
|
||||
};
|
||||
|
||||
template<class Char, class Traits, class Allocator, std::size_t N>
|
||||
struct plain_return_type_2<arithmetic_action<plus_action>,
|
||||
std::basic_string<Char, Traits, Allocator>,
|
||||
Char[N]> {
|
||||
typedef std::basic_string<Char, Traits, Allocator> type;
|
||||
};
|
||||
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
352
include/boost/lambda/detail/operators.hpp
Normal file
352
include/boost/lambda/detail/operators.hpp
Normal file
@@ -0,0 +1,352 @@
|
||||
// Boost Lambda Library - operators.hpp --------------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// ---------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_OPERATORS_HPP
|
||||
#define BOOST_LAMBDA_OPERATORS_HPP
|
||||
|
||||
#include "boost/lambda/detail/is_instance_of.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
#if defined BOOST_LAMBDA_BE1
|
||||
#error "Multiple defines of BOOST_LAMBDA_BE1"
|
||||
#endif
|
||||
|
||||
// For all BOOSTA_LAMBDA_BE* macros:
|
||||
|
||||
// CONSTA must be either 'A' or 'const A'
|
||||
// CONSTB must be either 'B' or 'const B'
|
||||
|
||||
// It is stupid to have the names A and B as macro arguments, but it avoids
|
||||
// the need to pass in emtpy macro arguments, which gives warnings on some
|
||||
// compilers
|
||||
|
||||
#define BOOST_LAMBDA_BE1(OPER_NAME, ACTION, CONSTA, CONSTB, CONVERSION) \
|
||||
template<class Arg, class B> \
|
||||
inline const \
|
||||
lambda_functor< \
|
||||
lambda_functor_base< \
|
||||
ACTION, \
|
||||
tuple<lambda_functor<Arg>, typename const_copy_argument <CONSTB>::type> \
|
||||
> \
|
||||
> \
|
||||
OPER_NAME (const lambda_functor<Arg>& a, CONSTB& b) { \
|
||||
return \
|
||||
lambda_functor_base< \
|
||||
ACTION, \
|
||||
tuple<lambda_functor<Arg>, typename const_copy_argument <CONSTB>::type>\
|
||||
> \
|
||||
(tuple<lambda_functor<Arg>, typename const_copy_argument <CONSTB>::type>(a, b)); \
|
||||
}
|
||||
|
||||
|
||||
#if defined BOOST_LAMBDA_BE2
|
||||
#error "Multiple defines of BOOST_LAMBDA_BE2"
|
||||
#endif
|
||||
|
||||
#define BOOST_LAMBDA_BE2(OPER_NAME, ACTION, CONSTA, CONSTB, CONVERSION) \
|
||||
template<class A, class Arg> \
|
||||
inline const \
|
||||
lambda_functor< \
|
||||
lambda_functor_base< \
|
||||
ACTION, \
|
||||
tuple<typename CONVERSION <CONSTA>::type, lambda_functor<Arg> > \
|
||||
> \
|
||||
> \
|
||||
OPER_NAME (CONSTA& a, const lambda_functor<Arg>& b) { \
|
||||
return \
|
||||
lambda_functor_base< \
|
||||
ACTION, \
|
||||
tuple<typename CONVERSION <CONSTA>::type, lambda_functor<Arg> > \
|
||||
> \
|
||||
(tuple<typename CONVERSION <CONSTA>::type, lambda_functor<Arg> >(a, b)); \
|
||||
}
|
||||
|
||||
|
||||
#if defined BOOST_LAMBDA_BE3
|
||||
#error "Multiple defines of BOOST_LAMBDA_BE3"
|
||||
#endif
|
||||
|
||||
#define BOOST_LAMBDA_BE3(OPER_NAME, ACTION, CONSTA, CONSTB, CONVERSION) \
|
||||
template<class ArgA, class ArgB> \
|
||||
inline const \
|
||||
lambda_functor< \
|
||||
lambda_functor_base< \
|
||||
ACTION, \
|
||||
tuple<lambda_functor<ArgA>, lambda_functor<ArgB> > \
|
||||
> \
|
||||
> \
|
||||
OPER_NAME (const lambda_functor<ArgA>& a, const lambda_functor<ArgB>& b) { \
|
||||
return \
|
||||
lambda_functor_base< \
|
||||
ACTION, \
|
||||
tuple<lambda_functor<ArgA>, lambda_functor<ArgB> > \
|
||||
> \
|
||||
(tuple<lambda_functor<ArgA>, lambda_functor<ArgB> >(a, b)); \
|
||||
}
|
||||
|
||||
#if defined BOOST_LAMBDA_BE
|
||||
#error "Multiple defines of BOOST_LAMBDA_BE"
|
||||
#endif
|
||||
|
||||
#define BOOST_LAMBDA_BE(OPER_NAME, ACTION, CONSTA, CONSTB, CONST_CONVERSION) \
|
||||
BOOST_LAMBDA_BE1(OPER_NAME, ACTION, CONSTA, CONSTB, CONST_CONVERSION) \
|
||||
BOOST_LAMBDA_BE2(OPER_NAME, ACTION, CONSTA, CONSTB, CONST_CONVERSION) \
|
||||
BOOST_LAMBDA_BE3(OPER_NAME, ACTION, CONSTA, CONSTB, CONST_CONVERSION)
|
||||
|
||||
#define BOOST_LAMBDA_EMPTY()
|
||||
|
||||
BOOST_LAMBDA_BE(operator+, arithmetic_action<plus_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator-, arithmetic_action<minus_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator*, arithmetic_action<multiply_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator/, arithmetic_action<divide_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator%, arithmetic_action<remainder_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator<<, bitwise_action<leftshift_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator>>, bitwise_action<rightshift_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator&, bitwise_action<and_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator|, bitwise_action<or_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator^, bitwise_action<xor_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator&&, logical_action<and_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator||, logical_action<or_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator<, relational_action<less_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator>, relational_action<greater_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator<=, relational_action<lessorequal_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator>=, relational_action<greaterorequal_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator==, relational_action<equal_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE(operator!=, relational_action<notequal_action>, const A, const B, const_copy_argument)
|
||||
|
||||
BOOST_LAMBDA_BE(operator+=, arithmetic_assignment_action<plus_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator-=, arithmetic_assignment_action<minus_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator*=, arithmetic_assignment_action<multiply_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator/=, arithmetic_assignment_action<divide_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator%=, arithmetic_assignment_action<remainder_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator<<=, bitwise_assignment_action<leftshift_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator>>=, bitwise_assignment_action<rightshift_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator&=, bitwise_assignment_action<and_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator|=, bitwise_assignment_action<or_action>, A, const B, reference_argument)
|
||||
BOOST_LAMBDA_BE(operator^=, bitwise_assignment_action<xor_action>, A, const B, reference_argument)
|
||||
|
||||
|
||||
// A special trick for comma operator for correct preprocessing
|
||||
#if defined BOOST_LAMBDA_COMMA_OPERATOR_NAME
|
||||
#error "Multiple defines of BOOST_LAMBDA_COMMA_OPERATOR_NAME"
|
||||
#endif
|
||||
|
||||
#define BOOST_LAMBDA_COMMA_OPERATOR_NAME operator,
|
||||
|
||||
BOOST_LAMBDA_BE1(BOOST_LAMBDA_COMMA_OPERATOR_NAME, other_action<comma_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE2(BOOST_LAMBDA_COMMA_OPERATOR_NAME, other_action<comma_action>, const A, const B, const_copy_argument)
|
||||
BOOST_LAMBDA_BE3(BOOST_LAMBDA_COMMA_OPERATOR_NAME, other_action<comma_action>, const A, const B, const_copy_argument)
|
||||
|
||||
|
||||
|
||||
namespace detail {
|
||||
|
||||
// special cases for ostream& << Any and istream& >> Any ---------------
|
||||
// the actual stream classes may vary and thus a specialisation for,
|
||||
// say ostream& does not match (the general case above is chosen).
|
||||
// Therefore we specialise for non-const reference:
|
||||
// if the left argument is a stream, we store the stream as reference
|
||||
// if it is something else, we store a const plain by default
|
||||
|
||||
// Note that the overloading is const vs. non-const first argument
|
||||
|
||||
|
||||
template<class T> struct convert_ostream_to_ref_others_to_c_plain_by_default {
|
||||
typedef typename detail::IF<
|
||||
is_instance_of_2<
|
||||
T, std::basic_ostream
|
||||
>::value,
|
||||
T&,
|
||||
typename const_copy_argument <T>::type
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
template<class T> struct convert_istream_to_ref_others_to_c_plain_by_default {
|
||||
typedef typename detail::IF<
|
||||
is_instance_of_2<
|
||||
T, std::basic_istream
|
||||
>::value,
|
||||
T&,
|
||||
typename const_copy_argument <T>::type
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
} // detail
|
||||
|
||||
BOOST_LAMBDA_BE2(operator<<, bitwise_action< leftshift_action>, A, const B, detail::convert_ostream_to_ref_others_to_c_plain_by_default)
|
||||
BOOST_LAMBDA_BE2(operator>>, bitwise_action< rightshift_action>, A, const B, detail::convert_istream_to_ref_others_to_c_plain_by_default)
|
||||
|
||||
|
||||
// special case for io_manipulators.
|
||||
// function references cannot be given as arguments to lambda operator
|
||||
// expressions in general. With << and >> the use of manipulators is
|
||||
// so common, that specializations are provided to make them work.
|
||||
|
||||
template<class Arg, class Ret, class ManipArg>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
bitwise_action<leftshift_action>,
|
||||
tuple<lambda_functor<Arg>, Ret(&)(ManipArg)>
|
||||
>
|
||||
>
|
||||
operator<<(const lambda_functor<Arg>& a, Ret(&b)(ManipArg))
|
||||
{
|
||||
return
|
||||
lambda_functor_base<
|
||||
bitwise_action<leftshift_action>,
|
||||
tuple<lambda_functor<Arg>, Ret(&)(ManipArg)>
|
||||
>
|
||||
( tuple<lambda_functor<Arg>, Ret(&)(ManipArg)>(a, b) );
|
||||
}
|
||||
|
||||
template<class Arg, class Ret, class ManipArg>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
bitwise_action<rightshift_action>,
|
||||
tuple<lambda_functor<Arg>, Ret(&)(ManipArg)>
|
||||
>
|
||||
>
|
||||
operator>>(const lambda_functor<Arg>& a, Ret(&b)(ManipArg))
|
||||
{
|
||||
return
|
||||
lambda_functor_base<
|
||||
bitwise_action<rightshift_action>,
|
||||
tuple<lambda_functor<Arg>, Ret(&)(ManipArg)>
|
||||
>
|
||||
( tuple<lambda_functor<Arg>, Ret(&)(ManipArg)>(a, b) );
|
||||
}
|
||||
|
||||
|
||||
// (+ and -) take their arguments as const references.
|
||||
// This has consquences with pointer artihmetic
|
||||
// E.g int a[]; ... *a = 1 works but not *(a+1) = 1.
|
||||
// the result of a+1 would be const
|
||||
// To make the latter work too,
|
||||
// non-const arrays are taken as non-const and stored as non-const as well.
|
||||
#if defined BOOST_LAMBDA_PTR_ARITHMETIC_E1
|
||||
#error "Multiple defines of BOOST_LAMBDA_PTR_ARITHMETIC_E1"
|
||||
#endif
|
||||
|
||||
#define BOOST_LAMBDA_PTR_ARITHMETIC_E1(OPER_NAME, ACTION, CONSTB) \
|
||||
template<class Arg, int N, class B> \
|
||||
inline const \
|
||||
lambda_functor< \
|
||||
lambda_functor_base<ACTION, tuple<lambda_functor<Arg>, CONSTB(&)[N]> > \
|
||||
> \
|
||||
OPER_NAME (const lambda_functor<Arg>& a, CONSTB(&b)[N]) \
|
||||
{ \
|
||||
return \
|
||||
lambda_functor_base<ACTION, tuple<lambda_functor<Arg>, CONSTB(&)[N]> > \
|
||||
(tuple<lambda_functor<Arg>, CONSTB(&)[N]>(a, b)); \
|
||||
}
|
||||
|
||||
|
||||
#if defined BOOST_LAMBDA_PTR_ARITHMETIC_E2
|
||||
#error "Multiple defines of BOOST_LAMBDA_PTR_ARITHMETIC_E2"
|
||||
#endif
|
||||
|
||||
#define BOOST_LAMBDA_PTR_ARITHMETIC_E2(OPER_NAME, ACTION, CONSTA) \
|
||||
template<int N, class A, class Arg> \
|
||||
inline const \
|
||||
lambda_functor< \
|
||||
lambda_functor_base<ACTION, tuple<CONSTA(&)[N], lambda_functor<Arg> > > \
|
||||
> \
|
||||
OPER_NAME (CONSTA(&a)[N], const lambda_functor<Arg>& b) \
|
||||
{ \
|
||||
return \
|
||||
lambda_functor_base<ACTION, tuple<CONSTA(&)[N], lambda_functor<Arg> > > \
|
||||
(tuple<CONSTA(&)[N], lambda_functor<Arg> >(a, b)); \
|
||||
}
|
||||
|
||||
|
||||
BOOST_LAMBDA_PTR_ARITHMETIC_E1(operator+, arithmetic_action<plus_action>, B)
|
||||
BOOST_LAMBDA_PTR_ARITHMETIC_E2(operator+, arithmetic_action<plus_action>, A)
|
||||
BOOST_LAMBDA_PTR_ARITHMETIC_E1(operator+, arithmetic_action<plus_action>,const B)
|
||||
BOOST_LAMBDA_PTR_ARITHMETIC_E2(operator+, arithmetic_action<plus_action>,const A)
|
||||
|
||||
|
||||
//BOOST_LAMBDA_PTR_ARITHMETIC_E1(operator-, arithmetic_action<minus_action>)
|
||||
// This is not needed, since the result of ptr-ptr is an rvalue anyway
|
||||
|
||||
BOOST_LAMBDA_PTR_ARITHMETIC_E2(operator-, arithmetic_action<minus_action>, A)
|
||||
BOOST_LAMBDA_PTR_ARITHMETIC_E2(operator-, arithmetic_action<minus_action>, const A)
|
||||
|
||||
|
||||
#undef BOOST_LAMBDA_BE1
|
||||
#undef BOOST_LAMBDA_BE2
|
||||
#undef BOOST_LAMBDA_BE3
|
||||
#undef BOOST_LAMBDA_BE
|
||||
#undef BOOST_LAMBDA_COMMA_OPERATOR_NAME
|
||||
|
||||
#undef BOOST_LAMBDA_PTR_ARITHMETIC_E1
|
||||
#undef BOOST_LAMBDA_PTR_ARITHMETIC_E2
|
||||
|
||||
|
||||
// ---------------------------------------------------------------------
|
||||
// unary operators -----------------------------------------------------
|
||||
// ---------------------------------------------------------------------
|
||||
|
||||
#if defined BOOST_LAMBDA_UE
|
||||
#error "Multiple defines of BOOST_LAMBDA_UE"
|
||||
#endif
|
||||
|
||||
#define BOOST_LAMBDA_UE(OPER_NAME, ACTION) \
|
||||
template<class Arg> \
|
||||
inline const \
|
||||
lambda_functor<lambda_functor_base<ACTION, tuple<lambda_functor<Arg> > > > \
|
||||
OPER_NAME (const lambda_functor<Arg>& a) \
|
||||
{ \
|
||||
return \
|
||||
lambda_functor_base<ACTION, tuple<lambda_functor<Arg> > > \
|
||||
( tuple<lambda_functor<Arg> >(a) ); \
|
||||
}
|
||||
|
||||
|
||||
BOOST_LAMBDA_UE(operator+, unary_arithmetic_action<plus_action>)
|
||||
BOOST_LAMBDA_UE(operator-, unary_arithmetic_action<minus_action>)
|
||||
BOOST_LAMBDA_UE(operator~, bitwise_action<not_action>)
|
||||
BOOST_LAMBDA_UE(operator!, logical_action<not_action>)
|
||||
BOOST_LAMBDA_UE(operator++, pre_increment_decrement_action<increment_action>)
|
||||
BOOST_LAMBDA_UE(operator--, pre_increment_decrement_action<decrement_action>)
|
||||
BOOST_LAMBDA_UE(operator*, other_action<contentsof_action>)
|
||||
BOOST_LAMBDA_UE(operator&, other_action<addressof_action>)
|
||||
|
||||
#if defined BOOST_LAMBDA_POSTFIX_UE
|
||||
#error "Multiple defines of BOOST_LAMBDA_POSTFIX_UE"
|
||||
#endif
|
||||
|
||||
#define BOOST_LAMBDA_POSTFIX_UE(OPER_NAME, ACTION) \
|
||||
template<class Arg> \
|
||||
inline const \
|
||||
lambda_functor<lambda_functor_base<ACTION, tuple<lambda_functor<Arg> > > > \
|
||||
OPER_NAME (const lambda_functor<Arg>& a, int) \
|
||||
{ \
|
||||
return \
|
||||
lambda_functor_base<ACTION, tuple<lambda_functor<Arg> > > \
|
||||
( tuple<lambda_functor<Arg> >(a) ); \
|
||||
}
|
||||
|
||||
|
||||
BOOST_LAMBDA_POSTFIX_UE(operator++, post_increment_decrement_action<increment_action>)
|
||||
BOOST_LAMBDA_POSTFIX_UE(operator--, post_increment_decrement_action<decrement_action>)
|
||||
|
||||
#undef BOOST_LAMBDA_UE
|
||||
#undef BOOST_LAMBDA_POSTFIX_UE
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
325
include/boost/lambda/detail/ret.hpp
Normal file
325
include/boost/lambda/detail/ret.hpp
Normal file
@@ -0,0 +1,325 @@
|
||||
// Boost Lambda Library ret.hpp -----------------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
|
||||
#ifndef BOOST_LAMBDA_RET_HPP
|
||||
#define BOOST_LAMBDA_RET_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// TODO:
|
||||
|
||||
// Add specializations for function references for ret, protect and unlambda
|
||||
// e.g void foo(); unlambda(foo); fails, as it would add a const qualifier
|
||||
// for a function type.
|
||||
// on the other hand unlambda(*foo) does work
|
||||
|
||||
|
||||
// -- ret -------------------------
|
||||
// the explicit return type template
|
||||
|
||||
// TODO: It'd be nice to make ret a nop for other than lambda functors
|
||||
// but causes an ambiguiyty with gcc (not with KCC), check what is the
|
||||
// right interpretation.
|
||||
|
||||
// // ret for others than lambda functors has no effect
|
||||
// template <class U, class T>
|
||||
// inline const T& ret(const T& t) { return t; }
|
||||
|
||||
|
||||
template<class RET, class Arg>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
explicit_return_type_action<RET>,
|
||||
tuple<lambda_functor<Arg> >
|
||||
>
|
||||
>
|
||||
ret(const lambda_functor<Arg>& a1)
|
||||
{
|
||||
return
|
||||
lambda_functor_base<
|
||||
explicit_return_type_action<RET>,
|
||||
tuple<lambda_functor<Arg> >
|
||||
>
|
||||
(tuple<lambda_functor<Arg> >(a1));
|
||||
}
|
||||
|
||||
// protect ------------------
|
||||
|
||||
// protecting others than lambda functors has no effect
|
||||
template <class T>
|
||||
inline const T& protect(const T& t) { return t; }
|
||||
|
||||
template<class Arg>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
protect_action,
|
||||
tuple<lambda_functor<Arg> >
|
||||
>
|
||||
>
|
||||
protect(const lambda_functor<Arg>& a1)
|
||||
{
|
||||
return
|
||||
lambda_functor_base<
|
||||
protect_action,
|
||||
tuple<lambda_functor<Arg> >
|
||||
>
|
||||
(tuple<lambda_functor<Arg> >(a1));
|
||||
}
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
|
||||
// Hides the lambda functorness of a lambda functor.
|
||||
// After this, the functor is immune to argument substitution, etc.
|
||||
// This can be used, e.g. to make it safe to pass lambda functors as
|
||||
// arguments to functions, which might use them as target functions
|
||||
|
||||
// note, unlambda and protect are different things. Protect hides the lambda
|
||||
// functor for one application, unlambda for good.
|
||||
|
||||
template <class LambdaFunctor>
|
||||
class non_lambda_functor
|
||||
{
|
||||
LambdaFunctor lf;
|
||||
public:
|
||||
|
||||
// This functor defines the result_type typedef.
|
||||
// The result type must be deducible without knowing the arguments
|
||||
|
||||
template <class SigArgs> struct sig {
|
||||
typedef typename
|
||||
LambdaFunctor::inherited::
|
||||
template sig<typename SigArgs::tail_type>::type type;
|
||||
};
|
||||
|
||||
explicit non_lambda_functor(const LambdaFunctor& a) : lf(a) {}
|
||||
|
||||
typename LambdaFunctor::nullary_return_type
|
||||
operator()() const {
|
||||
return lf.template
|
||||
call<typename LambdaFunctor::nullary_return_type>
|
||||
(cnull_type(), cnull_type(), cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A>
|
||||
typename sig<tuple<const non_lambda_functor, A&> >::type
|
||||
operator()(A& a) const {
|
||||
return lf.template call<typename sig<tuple<const non_lambda_functor, A&> >::type >(a, cnull_type(), cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
typename sig<tuple<const non_lambda_functor, A&, B&> >::type
|
||||
operator()(A& a, B& b) const {
|
||||
return lf.template call<typename sig<tuple<const non_lambda_functor, A&, B&> >::type >(a, b, cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B, class C>
|
||||
typename sig<tuple<const non_lambda_functor, A&, B&, C&> >::type
|
||||
operator()(A& a, B& b, C& c) const {
|
||||
return lf.template call<typename sig<tuple<const non_lambda_functor, A&, B&, C&> >::type>(a, b, c, cnull_type());
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg>
|
||||
inline const Arg& unlambda(const Arg& a) { return a; }
|
||||
|
||||
template <class Arg>
|
||||
inline const non_lambda_functor<lambda_functor<Arg> >
|
||||
unlambda(const lambda_functor<Arg>& a)
|
||||
{
|
||||
return non_lambda_functor<lambda_functor<Arg> >(a);
|
||||
}
|
||||
|
||||
// Due to a language restriction, lambda functors cannot be made to
|
||||
// accept non-const rvalue arguments. Usually iterators do not return
|
||||
// temporaries, but sometimes they do. That's why a workaround is provided.
|
||||
// Note, that this potentially breaks const correctness, so be careful!
|
||||
|
||||
// any lambda functor can be turned into a const_incorrect_lambda_functor
|
||||
// The operator() takes arguments as consts and then casts constness
|
||||
// away. So this breaks const correctness!!! but is a necessary workaround
|
||||
// in some cases due to language limitations.
|
||||
// Note, that this is not a lambda_functor anymore, so it can not be used
|
||||
// as a sub lambda expression.
|
||||
|
||||
template <class LambdaFunctor>
|
||||
struct const_incorrect_lambda_functor {
|
||||
LambdaFunctor lf;
|
||||
public:
|
||||
|
||||
explicit const_incorrect_lambda_functor(const LambdaFunctor& a) : lf(a) {}
|
||||
|
||||
template <class SigArgs> struct sig {
|
||||
typedef typename
|
||||
LambdaFunctor::inherited::template
|
||||
sig<typename SigArgs::tail_type>::type type;
|
||||
};
|
||||
|
||||
// The nullary case is not needed (no arguments, no parameter type problems)
|
||||
|
||||
template<class A>
|
||||
typename sig<tuple<const const_incorrect_lambda_functor, A&> >::type
|
||||
operator()(const A& a) const {
|
||||
return lf.template call<typename sig<tuple<const const_incorrect_lambda_functor, A&> >::type >(const_cast<A&>(a), cnull_type(), cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
typename sig<tuple<const const_incorrect_lambda_functor, A&, B&> >::type
|
||||
operator()(const A& a, const B& b) const {
|
||||
return lf.template call<typename sig<tuple<const const_incorrect_lambda_functor, A&, B&> >::type >(const_cast<A&>(a), const_cast<B&>(b), cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B, class C>
|
||||
typename sig<tuple<const const_incorrect_lambda_functor, A&, B&, C&> >::type
|
||||
operator()(const A& a, const B& b, const C& c) const {
|
||||
return lf.template call<typename sig<tuple<const const_incorrect_lambda_functor, A&, B&, C&> >::type>(const_cast<A&>(a), const_cast<B&>(b), const_cast<C&>(c), cnull_type());
|
||||
}
|
||||
};
|
||||
|
||||
// ------------------------------------------------------------------------
|
||||
// any lambda functor can be turned into a const_parameter_lambda_functor
|
||||
// The operator() takes arguments as const.
|
||||
// This is useful if lambda functors are called with non-const rvalues.
|
||||
// Note, that this is not a lambda_functor anymore, so it can not be used
|
||||
// as a sub lambda expression.
|
||||
|
||||
template <class LambdaFunctor>
|
||||
struct const_parameter_lambda_functor {
|
||||
LambdaFunctor lf;
|
||||
public:
|
||||
|
||||
explicit const_parameter_lambda_functor(const LambdaFunctor& a) : lf(a) {}
|
||||
|
||||
template <class SigArgs> struct sig {
|
||||
typedef typename
|
||||
LambdaFunctor::inherited::template
|
||||
sig<typename SigArgs::tail_type>::type type;
|
||||
};
|
||||
|
||||
// The nullary case is not needed: no arguments, no constness problems.
|
||||
|
||||
template<class A>
|
||||
typename sig<tuple<const const_parameter_lambda_functor, const A&> >::type
|
||||
operator()(const A& a) const {
|
||||
return lf.template call<typename sig<tuple<const const_parameter_lambda_functor, const A&> >::type >(a, cnull_type(), cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B>
|
||||
typename sig<tuple<const const_parameter_lambda_functor, const A&, const B&> >::type
|
||||
operator()(const A& a, const B& b) const {
|
||||
return lf.template call<typename sig<tuple<const const_parameter_lambda_functor, const A&, const B&> >::type >(a, b, cnull_type(), cnull_type());
|
||||
}
|
||||
|
||||
template<class A, class B, class C>
|
||||
typename sig<tuple<const const_parameter_lambda_functor, const A&, const B&, const C&>
|
||||
>::type
|
||||
operator()(const A& a, const B& b, const C& c) const {
|
||||
return lf.template call<typename sig<tuple<const const_parameter_lambda_functor, const A&, const B&, const C&> >::type>(a, b, c, cnull_type());
|
||||
}
|
||||
};
|
||||
|
||||
template <class Arg>
|
||||
inline const const_incorrect_lambda_functor<lambda_functor<Arg> >
|
||||
break_const(const lambda_functor<Arg>& lf)
|
||||
{
|
||||
return const_incorrect_lambda_functor<lambda_functor<Arg> >(lf);
|
||||
}
|
||||
|
||||
|
||||
template <class Arg>
|
||||
inline const const_parameter_lambda_functor<lambda_functor<Arg> >
|
||||
const_parameters(const lambda_functor<Arg>& lf)
|
||||
{
|
||||
return const_parameter_lambda_functor<lambda_functor<Arg> >(lf);
|
||||
}
|
||||
|
||||
// make void ------------------------------------------------
|
||||
// make_void( x ) turns a lambda functor x with some return type y into
|
||||
// another lambda functor, which has a void return type
|
||||
// when called, the original return type is discarded
|
||||
|
||||
// we use this action. The action class will be called, which means that
|
||||
// the wrapped lambda functor is evaluated, but we just don't do anything
|
||||
// with the result.
|
||||
struct voidifier_action {
|
||||
template<class Ret, class A> static void apply(A&) {}
|
||||
};
|
||||
|
||||
template<class Args> struct return_type_N<voidifier_action, Args> {
|
||||
typedef void type;
|
||||
};
|
||||
|
||||
template<class Arg1>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
action<1, voidifier_action>,
|
||||
tuple<lambda_functor<Arg1> >
|
||||
>
|
||||
>
|
||||
make_void(const lambda_functor<Arg1>& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
action<1, voidifier_action>,
|
||||
tuple<lambda_functor<Arg1> >
|
||||
>
|
||||
(tuple<lambda_functor<Arg1> > (a1));
|
||||
}
|
||||
|
||||
// for non-lambda functors, make_void does nothing
|
||||
// (the argument gets evaluated immediately)
|
||||
|
||||
template<class Arg1>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<do_nothing_action, null_type>
|
||||
>
|
||||
make_void(const Arg1&) {
|
||||
return
|
||||
lambda_functor_base<do_nothing_action, null_type>();
|
||||
}
|
||||
|
||||
// std_functor -----------------------------------------------------
|
||||
|
||||
// The STL uses the result_type typedef as the convention to let binders know
|
||||
// the return type of a function object.
|
||||
// LL uses the sig template.
|
||||
// To let LL know that the function object has the result_type typedef
|
||||
// defined, it can be wrapped with the std_functor function.
|
||||
|
||||
|
||||
// Just inherit form the template parameter (the standard functor),
|
||||
// and provide a sig template. So we have a class which is still the
|
||||
// same functor + the sig template.
|
||||
|
||||
template<class T>
|
||||
struct result_type_to_sig : public T {
|
||||
template<class Args> struct sig { typedef typename T::result_type type; };
|
||||
result_type_to_sig(const T& t) : T(t) {}
|
||||
};
|
||||
|
||||
template<class F>
|
||||
inline result_type_to_sig<F> std_functor(const F& f) { return f; }
|
||||
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
269
include/boost/lambda/detail/return_type_traits.hpp
Normal file
269
include/boost/lambda/detail/return_type_traits.hpp
Normal file
@@ -0,0 +1,269 @@
|
||||
// return_type_traits.hpp -- Boost Lambda Library ---------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
|
||||
#ifndef BOOST_LAMBDA_RETURN_TYPE_TRAITS_HPP
|
||||
#define BOOST_LAMBDA_RETURN_TYPE_TRAITS_HPP
|
||||
|
||||
#include "boost/mpl/has_xxx.hpp"
|
||||
|
||||
#include <cstddef> // needed for the ptrdiff_t
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// Much of the type deduction code for standard arithmetic types
|
||||
// from Gary Powell
|
||||
|
||||
// different arities:
|
||||
template <class Act, class A1> struct return_type_1; // 1-ary actions
|
||||
template <class Act, class A1, class A2> struct return_type_2; // 2-ary
|
||||
template <class Act, class Args> struct return_type_N; // >3- ary
|
||||
|
||||
template <class Act, class A1> struct return_type_1_prot;
|
||||
template <class Act, class A1, class A2> struct return_type_2_prot; // 2-ary
|
||||
template <class Act, class A1> struct return_type_N_prot; // >3-ary
|
||||
|
||||
|
||||
namespace detail {
|
||||
|
||||
template<class> class return_type_deduction_failure {};
|
||||
|
||||
// In some cases return type deduction should fail (an invalid lambda
|
||||
// expression). Sometimes the lambda expression can be ok, the return type
|
||||
// just is not deducible (user defined operators). Then return type deduction
|
||||
// should never be entered at all, and the use of ret<> does this.
|
||||
// However, for nullary lambda functors, return type deduction is always
|
||||
// entered, and there seems to be no way around this.
|
||||
|
||||
// (the return type is part of the prototype of the non-template
|
||||
// operator()(). The prototype is instantiated, even though the body
|
||||
// is not.)
|
||||
|
||||
// So, in the case the return type deduction should fail, it should not
|
||||
// fail directly, but rather result in a valid but wrong return type,
|
||||
// causing a compile time error only if the function is really called.
|
||||
|
||||
|
||||
|
||||
} // end detail
|
||||
|
||||
|
||||
|
||||
// return_type_X_prot classes --------------------------------------------
|
||||
// These classes are the first layer that gets instantiated from the
|
||||
// lambda_functor_base sig templates. It will check whether
|
||||
// the action is protectable and one of arguments is "protected" or its
|
||||
// evaluation will otherwise result in another lambda functor.
|
||||
// If this is a case, the result type will be another lambda functor.
|
||||
|
||||
// The arguments are always non-reference types, except for comma action
|
||||
// where the right argument can be a reference too. This is because it
|
||||
// matters (in the builtin case) whether the argument is an lvalue or
|
||||
// rvalue: int i; i, 1 -> rvalue; 1, i -> lvalue
|
||||
|
||||
template <class Act, class A> struct return_type_1_prot {
|
||||
public:
|
||||
typedef typename
|
||||
detail::IF<
|
||||
is_protectable<Act>::value && is_lambda_functor<A>::value,
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
Act,
|
||||
tuple<typename detail::remove_reference_and_cv<A>::type>
|
||||
>
|
||||
>,
|
||||
typename return_type_1<Act, A>::type
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
// take care of the unavoidable instantiation for nullary case
|
||||
template<class Act> struct return_type_1_prot<Act, null_type> {
|
||||
typedef null_type type;
|
||||
};
|
||||
|
||||
// Unary actions (result from unary operators)
|
||||
// do not have a default return type.
|
||||
template<class Act, class A> struct return_type_1 {
|
||||
typedef typename
|
||||
detail::return_type_deduction_failure<return_type_1> type;
|
||||
};
|
||||
|
||||
|
||||
namespace detail {
|
||||
|
||||
template <class T>
|
||||
class protect_conversion {
|
||||
typedef typename boost::remove_reference<T>::type non_ref_T;
|
||||
public:
|
||||
|
||||
// add const to rvalues, so that all rvalues are stored as const in
|
||||
// the args tuple
|
||||
typedef typename detail::IF_type<
|
||||
boost::is_reference<T>::value && !boost::is_const<non_ref_T>::value,
|
||||
detail::identity_mapping<T>,
|
||||
const_copy_argument<non_ref_T> // handles funtion and array
|
||||
>::type type; // types correctly
|
||||
};
|
||||
|
||||
} // end detail
|
||||
|
||||
template <class Act, class A, class B> struct return_type_2_prot {
|
||||
|
||||
// experimental feature
|
||||
// We may have a lambda functor as a result type of a subexpression
|
||||
// (if protect) has been used.
|
||||
// Thus, if one of the parameter types is a lambda functor, the result
|
||||
// is a lambda functor as well.
|
||||
// We need to make a conservative choise here.
|
||||
// The resulting lambda functor stores all const reference arguments as
|
||||
// const copies. References to non-const are stored as such.
|
||||
// So if the source of the argument is a const open argument, a bound
|
||||
// argument stored as a const reference, or a function returning a
|
||||
// const reference, that information is lost. There is no way of
|
||||
// telling apart 'real const references' from just 'LL internal
|
||||
// const references' (or it would be really hard)
|
||||
|
||||
// The return type is a subclass of lambda_functor, which has a converting
|
||||
// copy constructor. It can copy any lambda functor, that has the same
|
||||
// action type and code, and a copy compatible argument tuple.
|
||||
|
||||
|
||||
typedef typename boost::remove_reference<A>::type non_ref_A;
|
||||
typedef typename boost::remove_reference<B>::type non_ref_B;
|
||||
|
||||
typedef typename
|
||||
detail::IF<
|
||||
is_protectable<Act>::value &&
|
||||
(is_lambda_functor<A>::value || is_lambda_functor<B>::value),
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
Act,
|
||||
tuple<typename detail::protect_conversion<A>::type,
|
||||
typename detail::protect_conversion<B>::type>
|
||||
>
|
||||
>,
|
||||
typename return_type_2<Act, non_ref_A, non_ref_B>::type
|
||||
>::RET type;
|
||||
};
|
||||
|
||||
// take care of the unavoidable instantiation for nullary case
|
||||
template<class Act> struct return_type_2_prot<Act, null_type, null_type> {
|
||||
typedef null_type type;
|
||||
};
|
||||
// take care of the unavoidable instantiation for nullary case
|
||||
template<class Act, class Other> struct return_type_2_prot<Act, Other, null_type> {
|
||||
typedef null_type type;
|
||||
};
|
||||
// take care of the unavoidable instantiation for nullary case
|
||||
template<class Act, class Other> struct return_type_2_prot<Act, null_type, Other> {
|
||||
typedef null_type type;
|
||||
};
|
||||
|
||||
// comma is a special case, as the user defined operator can return
|
||||
// an lvalue (reference) too, hence it must be handled at this level.
|
||||
template<class A, class B>
|
||||
struct return_type_2_comma
|
||||
{
|
||||
typedef typename boost::remove_reference<A>::type non_ref_A;
|
||||
typedef typename boost::remove_reference<B>::type non_ref_B;
|
||||
|
||||
typedef typename
|
||||
detail::IF<
|
||||
is_protectable<other_action<comma_action> >::value && // it is protectable
|
||||
(is_lambda_functor<A>::value || is_lambda_functor<B>::value),
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
other_action<comma_action>,
|
||||
tuple<typename detail::protect_conversion<A>::type,
|
||||
typename detail::protect_conversion<B>::type>
|
||||
>
|
||||
>,
|
||||
typename
|
||||
return_type_2<other_action<comma_action>, non_ref_A, non_ref_B>::type
|
||||
>::RET type1;
|
||||
|
||||
// if no user defined return_type_2 (or plain_return_type_2) specialization
|
||||
// matches, then return the righthand argument
|
||||
typedef typename
|
||||
detail::IF<
|
||||
boost::is_same<type1, detail::unspecified>::value,
|
||||
B,
|
||||
type1
|
||||
>::RET type;
|
||||
|
||||
};
|
||||
|
||||
|
||||
// currently there are no protectable actions with > 2 args
|
||||
|
||||
template<class Act, class Args> struct return_type_N_prot {
|
||||
typedef typename return_type_N<Act, Args>::type type;
|
||||
};
|
||||
|
||||
// take care of the unavoidable instantiation for nullary case
|
||||
template<class Act> struct return_type_N_prot<Act, null_type> {
|
||||
typedef null_type type;
|
||||
};
|
||||
|
||||
// handle different kind of actions ------------------------
|
||||
|
||||
// use the return type given in the bind invocation as bind<Ret>(...)
|
||||
template<int I, class Args, class Ret>
|
||||
struct return_type_N<function_action<I, Ret>, Args> {
|
||||
typedef Ret type;
|
||||
};
|
||||
|
||||
// ::result_type support
|
||||
|
||||
namespace detail
|
||||
{
|
||||
|
||||
BOOST_MPL_HAS_XXX_TRAIT_DEF(result_type)
|
||||
|
||||
template<class F> struct get_result_type
|
||||
{
|
||||
typedef typename F::result_type type;
|
||||
};
|
||||
|
||||
template<class F, class A> struct get_sig
|
||||
{
|
||||
typedef typename function_adaptor<F>::template sig<A>::type type;
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
|
||||
// Ret is detail::unspecified, so try to deduce return type
|
||||
template<int I, class Args>
|
||||
struct return_type_N<function_action<I, detail::unspecified>, Args > {
|
||||
|
||||
// in the case of function action, the first element in Args is
|
||||
// some type of function
|
||||
typedef typename Args::head_type Func;
|
||||
typedef typename detail::remove_reference_and_cv<Func>::type plain_Func;
|
||||
|
||||
public:
|
||||
// pass the function to function_adaptor, and get the return type from
|
||||
// that
|
||||
typedef typename detail::IF<
|
||||
detail::has_result_type<plain_Func>::value,
|
||||
detail::get_result_type<plain_Func>,
|
||||
detail::get_sig<plain_Func, Args>
|
||||
>::RET::type type;
|
||||
};
|
||||
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
74
include/boost/lambda/detail/select_functions.hpp
Normal file
74
include/boost/lambda/detail/select_functions.hpp
Normal file
@@ -0,0 +1,74 @@
|
||||
// -- select_functions.hpp -- Boost Lambda Library --------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see http://www.boost.org
|
||||
|
||||
|
||||
#ifndef BOOST_LAMBDA_SELECT_FUNCTIONS_HPP
|
||||
#define BOOST_LAMBDA_SELECT_FUNCTIONS_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
namespace detail {
|
||||
|
||||
|
||||
// select functions -------------------------------
|
||||
template<class Any, CALL_TEMPLATE_ARGS>
|
||||
inline Any& select(Any& any, CALL_FORMAL_ARGS) { CALL_USE_ARGS; return any; }
|
||||
|
||||
|
||||
template<class Arg, CALL_TEMPLATE_ARGS>
|
||||
inline typename Arg::template sig<tuple<CALL_REFERENCE_TYPES> >::type
|
||||
select ( const lambda_functor<Arg>& op, CALL_FORMAL_ARGS ) {
|
||||
return op.template call<
|
||||
typename Arg::template sig<tuple<CALL_REFERENCE_TYPES> >::type
|
||||
>(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
template<class Arg, CALL_TEMPLATE_ARGS>
|
||||
inline typename Arg::template sig<tuple<CALL_REFERENCE_TYPES> >::type
|
||||
select ( lambda_functor<Arg>& op, CALL_FORMAL_ARGS) {
|
||||
return op.template call<
|
||||
typename Arg::template sig<tuple<CALL_REFERENCE_TYPES> >::type
|
||||
>(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
|
||||
// ------------------------------------------------------------------------
|
||||
// select functions where the return type is explicitly given
|
||||
// Note: on many functions, this return type is just discarded.
|
||||
// The select functions are inside a class template, and the return type
|
||||
// is a class template argument.
|
||||
// The first implementation used function templates with an explicitly
|
||||
// specified template parameter.
|
||||
// However, this resulted in ambiguous calls (at least with gcc 2.95.2
|
||||
// and edg 2.44). Not sure whether the compilers were right or wrong.
|
||||
|
||||
template<class RET> struct r_select {
|
||||
|
||||
// Any == RET
|
||||
template<class Any, CALL_TEMPLATE_ARGS>
|
||||
static
|
||||
inline RET go (Any& any, CALL_FORMAL_ARGS) { CALL_USE_ARGS; return any; }
|
||||
|
||||
|
||||
template<class Arg, CALL_TEMPLATE_ARGS>
|
||||
static
|
||||
inline RET go (const lambda_functor<Arg>& op, CALL_FORMAL_ARGS ) {
|
||||
return op.template call<RET>(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
template<class Arg, CALL_TEMPLATE_ARGS>
|
||||
static
|
||||
inline RET go (lambda_functor<Arg>& op, CALL_FORMAL_ARGS ) {
|
||||
return op.template call<RET>(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace detail
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
#endif
|
||||
27
include/boost/lambda/detail/suppress_unused.hpp
Normal file
27
include/boost/lambda/detail/suppress_unused.hpp
Normal file
@@ -0,0 +1,27 @@
|
||||
// Boost Lambda Library suppress_unused.hpp -----------------------------
|
||||
//
|
||||
// Copyright (C) 2009 Steven Watanabe
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// ------------------------------------------------------------
|
||||
|
||||
#ifndef BOOST_LAMBDA_SUPPRESS_UNUSED_HPP
|
||||
#define BOOST_LAMBDA_SUPPRESS_UNUSED_HPP
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
namespace detail {
|
||||
|
||||
template<class T>
|
||||
inline void suppress_unused_variable_warnings(const T&) {}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
1741
include/boost/lambda/exceptions.hpp
Normal file
1741
include/boost/lambda/exceptions.hpp
Normal file
File diff suppressed because it is too large
Load Diff
462
include/boost/lambda/if.hpp
Normal file
462
include/boost/lambda/if.hpp
Normal file
@@ -0,0 +1,462 @@
|
||||
// Boost Lambda Library -- if.hpp ------------------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000 Gary Powell (powellg@amazon.com)
|
||||
// Copyright (C) 2001-2002 Joel de Guzman
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// --------------------------------------------------------------------------
|
||||
|
||||
#if !defined(BOOST_LAMBDA_IF_HPP)
|
||||
#define BOOST_LAMBDA_IF_HPP
|
||||
|
||||
#include "boost/lambda/core.hpp"
|
||||
|
||||
// Arithmetic type promotion needed for if_then_else_return
|
||||
#include "boost/lambda/detail/operator_actions.hpp"
|
||||
#include "boost/lambda/detail/operator_return_type_traits.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// -- if control construct actions ----------------------
|
||||
|
||||
class ifthen_action {};
|
||||
class ifthenelse_action {};
|
||||
class ifthenelsereturn_action {};
|
||||
|
||||
// Specialization for if_then.
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<ifthen_action, Args> {
|
||||
public:
|
||||
Args args;
|
||||
template <class T> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
if (detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS))
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
};
|
||||
|
||||
// If Then
|
||||
template <class Arg1, class Arg2>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
ifthen_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >
|
||||
>
|
||||
>
|
||||
if_then(const lambda_functor<Arg1>& a1, const lambda_functor<Arg2>& a2) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
ifthen_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >
|
||||
>
|
||||
( tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >(a1, a2) );
|
||||
}
|
||||
|
||||
|
||||
// Specialization for if_then_else.
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<ifthenelse_action, Args> {
|
||||
public:
|
||||
Args args;
|
||||
template <class T> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
if (detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS))
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
else
|
||||
detail::select(boost::tuples::get<2>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
|
||||
// If then else
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
ifthenelse_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2>, lambda_functor<Arg3> >
|
||||
>
|
||||
>
|
||||
if_then_else(const lambda_functor<Arg1>& a1, const lambda_functor<Arg2>& a2,
|
||||
const lambda_functor<Arg3>& a3) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
ifthenelse_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2>, lambda_functor<Arg3> >
|
||||
>
|
||||
(tuple<lambda_functor<Arg1>, lambda_functor<Arg2>, lambda_functor<Arg3> >
|
||||
(a1, a2, a3) );
|
||||
}
|
||||
|
||||
// Our version of operator?:()
|
||||
|
||||
template <class Arg1, class Arg2, class Arg3>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
other_action<ifthenelsereturn_action>,
|
||||
tuple<lambda_functor<Arg1>,
|
||||
typename const_copy_argument<Arg2>::type,
|
||||
typename const_copy_argument<Arg3>::type>
|
||||
>
|
||||
>
|
||||
if_then_else_return(const lambda_functor<Arg1>& a1,
|
||||
const Arg2 & a2,
|
||||
const Arg3 & a3) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
other_action<ifthenelsereturn_action>,
|
||||
tuple<lambda_functor<Arg1>,
|
||||
typename const_copy_argument<Arg2>::type,
|
||||
typename const_copy_argument<Arg3>::type>
|
||||
> ( tuple<lambda_functor<Arg1>,
|
||||
typename const_copy_argument<Arg2>::type,
|
||||
typename const_copy_argument<Arg3>::type> (a1, a2, a3) );
|
||||
}
|
||||
|
||||
namespace detail {
|
||||
|
||||
// return type specialization for conditional expression begins -----------
|
||||
// start reading below and move upwards
|
||||
|
||||
// PHASE 6:1
|
||||
// check if A is conbertible to B and B to A
|
||||
template<int Phase, bool AtoB, bool BtoA, bool SameType, class A, class B>
|
||||
struct return_type_2_ifthenelsereturn;
|
||||
|
||||
// if A can be converted to B and vice versa -> ambiguous
|
||||
template<int Phase, class A, class B>
|
||||
struct return_type_2_ifthenelsereturn<Phase, true, true, false, A, B> {
|
||||
typedef
|
||||
detail::return_type_deduction_failure<return_type_2_ifthenelsereturn> type;
|
||||
// ambiguous type in conditional expression
|
||||
};
|
||||
// if A can be converted to B and vice versa and are of same type
|
||||
template<int Phase, class A, class B>
|
||||
struct return_type_2_ifthenelsereturn<Phase, true, true, true, A, B> {
|
||||
typedef A type;
|
||||
};
|
||||
|
||||
|
||||
// A can be converted to B
|
||||
template<int Phase, class A, class B>
|
||||
struct return_type_2_ifthenelsereturn<Phase, true, false, false, A, B> {
|
||||
typedef B type;
|
||||
};
|
||||
|
||||
// B can be converted to A
|
||||
template<int Phase, class A, class B>
|
||||
struct return_type_2_ifthenelsereturn<Phase, false, true, false, A, B> {
|
||||
typedef A type;
|
||||
};
|
||||
|
||||
// neither can be converted. Then we drop the potential references, and
|
||||
// try again
|
||||
template<class A, class B>
|
||||
struct return_type_2_ifthenelsereturn<1, false, false, false, A, B> {
|
||||
// it is safe to add const, since the result will be an rvalue and thus
|
||||
// const anyway. The const are needed eg. if the types
|
||||
// are 'const int*' and 'void *'. The remaining type should be 'const void*'
|
||||
typedef const typename boost::remove_reference<A>::type plainA;
|
||||
typedef const typename boost::remove_reference<B>::type plainB;
|
||||
// TODO: Add support for volatile ?
|
||||
|
||||
typedef typename
|
||||
return_type_2_ifthenelsereturn<
|
||||
2,
|
||||
boost::is_convertible<plainA,plainB>::value,
|
||||
boost::is_convertible<plainB,plainA>::value,
|
||||
boost::is_same<plainA,plainB>::value,
|
||||
plainA,
|
||||
plainB>::type type;
|
||||
};
|
||||
|
||||
// PHASE 6:2
|
||||
template<class A, class B>
|
||||
struct return_type_2_ifthenelsereturn<2, false, false, false, A, B> {
|
||||
typedef
|
||||
detail::return_type_deduction_failure<return_type_2_ifthenelsereturn> type;
|
||||
// types_do_not_match_in_conditional_expression
|
||||
};
|
||||
|
||||
|
||||
|
||||
// PHASE 5: now we know that types are not arithmetic.
|
||||
template<class A, class B>
|
||||
struct non_numeric_types {
|
||||
typedef typename
|
||||
return_type_2_ifthenelsereturn<
|
||||
1, // phase 1
|
||||
is_convertible<A,B>::value,
|
||||
is_convertible<B,A>::value,
|
||||
is_same<A,B>::value,
|
||||
A,
|
||||
B>::type type;
|
||||
};
|
||||
|
||||
// PHASE 4 :
|
||||
// the base case covers arithmetic types with differing promote codes
|
||||
// use the type deduction of arithmetic_actions
|
||||
template<int CodeA, int CodeB, class A, class B>
|
||||
struct arithmetic_or_not {
|
||||
typedef typename
|
||||
return_type_2<arithmetic_action<plus_action>, A, B>::type type;
|
||||
// plus_action is just a random pick, has to be a concrete instance
|
||||
};
|
||||
|
||||
// this case covers the case of artihmetic types with the same promote codes.
|
||||
// non numeric deduction is used since e.g. integral promotion is not
|
||||
// performed with operator ?:
|
||||
template<int CodeA, class A, class B>
|
||||
struct arithmetic_or_not<CodeA, CodeA, A, B> {
|
||||
typedef typename non_numeric_types<A, B>::type type;
|
||||
};
|
||||
|
||||
// if either A or B has promote code -1 it is not an arithmetic type
|
||||
template<class A, class B>
|
||||
struct arithmetic_or_not <-1, -1, A, B> {
|
||||
typedef typename non_numeric_types<A, B>::type type;
|
||||
};
|
||||
template<int CodeB, class A, class B>
|
||||
struct arithmetic_or_not <-1, CodeB, A, B> {
|
||||
typedef typename non_numeric_types<A, B>::type type;
|
||||
};
|
||||
template<int CodeA, class A, class B>
|
||||
struct arithmetic_or_not <CodeA, -1, A, B> {
|
||||
typedef typename non_numeric_types<A, B>::type type;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
// PHASE 3 : Are the types same?
|
||||
// No, check if they are arithmetic or not
|
||||
template <class A, class B>
|
||||
struct same_or_not {
|
||||
typedef typename detail::remove_reference_and_cv<A>::type plainA;
|
||||
typedef typename detail::remove_reference_and_cv<B>::type plainB;
|
||||
|
||||
typedef typename
|
||||
arithmetic_or_not<
|
||||
detail::promote_code<plainA>::value,
|
||||
detail::promote_code<plainB>::value,
|
||||
A,
|
||||
B>::type type;
|
||||
};
|
||||
// Yes, clear.
|
||||
template <class A> struct same_or_not<A, A> {
|
||||
typedef A type;
|
||||
};
|
||||
|
||||
} // detail
|
||||
|
||||
// PHASE 2 : Perform first the potential array_to_pointer conversion
|
||||
template<class A, class B>
|
||||
struct return_type_2<other_action<ifthenelsereturn_action>, A, B> {
|
||||
|
||||
typedef typename detail::array_to_pointer<A>::type A1;
|
||||
typedef typename detail::array_to_pointer<B>::type B1;
|
||||
|
||||
typedef typename
|
||||
boost::add_const<typename detail::same_or_not<A1, B1>::type>::type type;
|
||||
};
|
||||
|
||||
// PHASE 1 : Deduction is based on the second and third operand
|
||||
|
||||
|
||||
// return type specialization for conditional expression ends -----------
|
||||
|
||||
|
||||
// Specialization of lambda_functor_base for if_then_else_return.
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<other_action<ifthenelsereturn_action>, Args> {
|
||||
public:
|
||||
Args args;
|
||||
|
||||
template <class SigArgs> struct sig {
|
||||
private:
|
||||
typedef typename detail::nth_return_type_sig<1, Args, SigArgs>::type ret1;
|
||||
typedef typename detail::nth_return_type_sig<2, Args, SigArgs>::type ret2;
|
||||
public:
|
||||
typedef typename return_type_2<
|
||||
other_action<ifthenelsereturn_action>, ret1, ret2
|
||||
>::type type;
|
||||
};
|
||||
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
return (detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS)) ?
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS)
|
||||
:
|
||||
detail::select(boost::tuples::get<2>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
};
|
||||
|
||||
// The code below is from Joel de Guzman, some name changes etc.
|
||||
// has been made.
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// if_then_else_composite
|
||||
//
|
||||
// This composite has two (2) forms:
|
||||
//
|
||||
// if_(condition)
|
||||
// [
|
||||
// statement
|
||||
// ]
|
||||
//
|
||||
// and
|
||||
//
|
||||
// if_(condition)
|
||||
// [
|
||||
// true_statement
|
||||
// ]
|
||||
// .else_
|
||||
// [
|
||||
// false_statement
|
||||
// ]
|
||||
//
|
||||
// where condition is an lambda_functor that evaluates to bool. If condition
|
||||
// is true, the true_statement (again an lambda_functor) is executed
|
||||
// otherwise, the false_statement (another lambda_functor) is executed. The
|
||||
// result type of this is void. Note the trailing underscore after
|
||||
// if_ and the leading dot and the trailing underscore before
|
||||
// and after .else_.
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CondT, typename ThenT, typename ElseT>
|
||||
struct if_then_else_composite {
|
||||
|
||||
typedef if_then_else_composite<CondT, ThenT, ElseT> self_t;
|
||||
|
||||
template <class SigArgs>
|
||||
struct sig { typedef void type; };
|
||||
|
||||
if_then_else_composite(
|
||||
CondT const& cond_,
|
||||
ThenT const& then_,
|
||||
ElseT const& else__)
|
||||
: cond(cond_), then(then_), else_(else__) {}
|
||||
|
||||
template <class Ret, CALL_TEMPLATE_ARGS>
|
||||
Ret call(CALL_FORMAL_ARGS) const
|
||||
{
|
||||
if (cond.internal_call(CALL_ACTUAL_ARGS))
|
||||
then.internal_call(CALL_ACTUAL_ARGS);
|
||||
else
|
||||
else_.internal_call(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
|
||||
CondT cond; ThenT then; ElseT else_; // lambda_functors
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CondT, typename ThenT>
|
||||
struct else_gen {
|
||||
|
||||
else_gen(CondT const& cond_, ThenT const& then_)
|
||||
: cond(cond_), then(then_) {}
|
||||
|
||||
template <typename ElseT>
|
||||
lambda_functor<if_then_else_composite<CondT, ThenT,
|
||||
typename as_lambda_functor<ElseT>::type> >
|
||||
operator[](ElseT const& else_)
|
||||
{
|
||||
typedef if_then_else_composite<CondT, ThenT,
|
||||
typename as_lambda_functor<ElseT>::type>
|
||||
result;
|
||||
|
||||
return result(cond, then, to_lambda_functor(else_));
|
||||
}
|
||||
|
||||
CondT cond; ThenT then;
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CondT, typename ThenT>
|
||||
struct if_then_composite {
|
||||
|
||||
template <class SigArgs>
|
||||
struct sig { typedef void type; };
|
||||
|
||||
if_then_composite(CondT const& cond_, ThenT const& then_)
|
||||
: cond(cond_), then(then_), else_(cond, then) {}
|
||||
|
||||
template <class Ret, CALL_TEMPLATE_ARGS>
|
||||
Ret call(CALL_FORMAL_ARGS) const
|
||||
{
|
||||
if (cond.internal_call(CALL_ACTUAL_ARGS))
|
||||
then.internal_call(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
|
||||
CondT cond; ThenT then; // lambda_functors
|
||||
else_gen<CondT, ThenT> else_;
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CondT>
|
||||
struct if_gen {
|
||||
|
||||
if_gen(CondT const& cond_)
|
||||
: cond(cond_) {}
|
||||
|
||||
template <typename ThenT>
|
||||
lambda_functor<if_then_composite<
|
||||
typename as_lambda_functor<CondT>::type,
|
||||
typename as_lambda_functor<ThenT>::type> >
|
||||
operator[](ThenT const& then) const
|
||||
{
|
||||
typedef if_then_composite<
|
||||
typename as_lambda_functor<CondT>::type,
|
||||
typename as_lambda_functor<ThenT>::type>
|
||||
result;
|
||||
|
||||
return result(
|
||||
to_lambda_functor(cond),
|
||||
to_lambda_functor(then));
|
||||
}
|
||||
|
||||
CondT cond;
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CondT>
|
||||
inline if_gen<CondT>
|
||||
if_(CondT const& cond)
|
||||
{
|
||||
return if_gen<CondT>(cond);
|
||||
}
|
||||
|
||||
|
||||
|
||||
} // lambda
|
||||
} // boost
|
||||
|
||||
#endif // BOOST_LAMBDA_IF_HPP
|
||||
|
||||
|
||||
29
include/boost/lambda/lambda.hpp
Normal file
29
include/boost/lambda/lambda.hpp
Normal file
@@ -0,0 +1,29 @@
|
||||
// -- lambda.hpp -- Boost Lambda Library -----------------------------------
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see http://lambda.cs.utu.fi
|
||||
|
||||
#ifndef BOOST_LAMBDA_LAMBDA_HPP
|
||||
#define BOOST_LAMBDA_LAMBDA_HPP
|
||||
|
||||
|
||||
#include "boost/lambda/core.hpp"
|
||||
|
||||
#ifdef BOOST_NO_FDECL_TEMPLATES_AS_TEMPLATE_TEMPLATE_PARAMS
|
||||
#include <istream>
|
||||
#include <ostream>
|
||||
#endif
|
||||
|
||||
#include "boost/lambda/detail/operator_actions.hpp"
|
||||
#include "boost/lambda/detail/operator_lambda_func_base.hpp"
|
||||
#include "boost/lambda/detail/operator_return_type_traits.hpp"
|
||||
|
||||
|
||||
#include "boost/lambda/detail/operators.hpp"
|
||||
#include "boost/lambda/detail/member_ptr.hpp"
|
||||
|
||||
#endif
|
||||
505
include/boost/lambda/loops.hpp
Normal file
505
include/boost/lambda/loops.hpp
Normal file
@@ -0,0 +1,505 @@
|
||||
// Boost Lambda Library -- loops.hpp ----------------------------------------
|
||||
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000 Gary Powell (powellg@amazon.com)
|
||||
// Copyright (c) 2001-2002 Joel de Guzman
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// --------------------------------------------------------------------------
|
||||
|
||||
#if !defined(BOOST_LAMBDA_LOOPS_HPP)
|
||||
#define BOOST_LAMBDA_LOOPS_HPP
|
||||
|
||||
#include "boost/lambda/core.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// -- loop control structure actions ----------------------
|
||||
|
||||
class forloop_action {};
|
||||
class forloop_no_body_action {};
|
||||
class whileloop_action {};
|
||||
class whileloop_no_body_action {};
|
||||
class dowhileloop_action {};
|
||||
class dowhileloop_no_body_action {};
|
||||
|
||||
|
||||
// For loop
|
||||
template <class Arg1, class Arg2, class Arg3, class Arg4>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
forloop_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2>,
|
||||
lambda_functor<Arg3>, lambda_functor<Arg4> >
|
||||
>
|
||||
>
|
||||
for_loop(const lambda_functor<Arg1>& a1, const lambda_functor<Arg2>& a2,
|
||||
const lambda_functor<Arg3>& a3, const lambda_functor<Arg4>& a4) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
forloop_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2>,
|
||||
lambda_functor<Arg3>, lambda_functor<Arg4> >
|
||||
>
|
||||
( tuple<lambda_functor<Arg1>, lambda_functor<Arg2>,
|
||||
lambda_functor<Arg3>, lambda_functor<Arg4> >(a1, a2, a3, a4)
|
||||
);
|
||||
}
|
||||
|
||||
// No body case.
|
||||
template <class Arg1, class Arg2, class Arg3>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
forloop_no_body_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2>, lambda_functor<Arg3> >
|
||||
>
|
||||
>
|
||||
for_loop(const lambda_functor<Arg1>& a1, const lambda_functor<Arg2>& a2,
|
||||
const lambda_functor<Arg3>& a3) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
forloop_no_body_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2>,
|
||||
lambda_functor<Arg3> >
|
||||
>
|
||||
( tuple<lambda_functor<Arg1>, lambda_functor<Arg2>,
|
||||
lambda_functor<Arg3> >(a1, a2, a3) );
|
||||
}
|
||||
|
||||
// While loop
|
||||
template <class Arg1, class Arg2>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
whileloop_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >
|
||||
>
|
||||
>
|
||||
while_loop(const lambda_functor<Arg1>& a1, const lambda_functor<Arg2>& a2) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
whileloop_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >
|
||||
>
|
||||
( tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >(a1, a2));
|
||||
}
|
||||
|
||||
// No body case.
|
||||
template <class Arg1>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
whileloop_no_body_action,
|
||||
tuple<lambda_functor<Arg1> >
|
||||
>
|
||||
>
|
||||
while_loop(const lambda_functor<Arg1>& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
whileloop_no_body_action,
|
||||
tuple<lambda_functor<Arg1> >
|
||||
>
|
||||
( tuple<lambda_functor<Arg1> >(a1) );
|
||||
}
|
||||
|
||||
|
||||
// Do While loop
|
||||
template <class Arg1, class Arg2>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
dowhileloop_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >
|
||||
>
|
||||
>
|
||||
do_while_loop(const lambda_functor<Arg1>& a1, const lambda_functor<Arg2>& a2) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
dowhileloop_action,
|
||||
tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >
|
||||
>
|
||||
( tuple<lambda_functor<Arg1>, lambda_functor<Arg2> >(a1, a2));
|
||||
}
|
||||
|
||||
// No body case.
|
||||
template <class Arg1>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
dowhileloop_no_body_action,
|
||||
tuple<lambda_functor<Arg1> >
|
||||
>
|
||||
>
|
||||
do_while_loop(const lambda_functor<Arg1>& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
dowhileloop_no_body_action,
|
||||
tuple<lambda_functor<Arg1> >
|
||||
>
|
||||
( tuple<lambda_functor<Arg1> >(a1));
|
||||
}
|
||||
|
||||
|
||||
// Control loop lambda_functor_base specializations.
|
||||
|
||||
// Specialization for for_loop.
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<forloop_action, Args> {
|
||||
public:
|
||||
Args args;
|
||||
template <class T> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
for(detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS);
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
detail::select(boost::tuples::get<2>(args), CALL_ACTUAL_ARGS))
|
||||
|
||||
detail::select(boost::tuples::get<3>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
};
|
||||
|
||||
// No body case
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<forloop_no_body_action, Args> {
|
||||
public:
|
||||
Args args;
|
||||
template <class T> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
for(detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS);
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
detail::select(boost::tuples::get<2>(args), CALL_ACTUAL_ARGS)) {}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// Specialization for while_loop.
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<whileloop_action, Args> {
|
||||
public:
|
||||
Args args;
|
||||
template <class T> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
while(detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS))
|
||||
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
};
|
||||
|
||||
// No body case
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<whileloop_no_body_action, Args> {
|
||||
public:
|
||||
Args args;
|
||||
template <class T> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
while(detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS)) {}
|
||||
}
|
||||
};
|
||||
|
||||
// Specialization for do_while_loop.
|
||||
// Note that the first argument is the condition.
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<dowhileloop_action, Args> {
|
||||
public:
|
||||
Args args;
|
||||
template <class T> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
do {
|
||||
detail::select(boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
} while (detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) );
|
||||
}
|
||||
};
|
||||
|
||||
// No body case
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<dowhileloop_no_body_action, Args> {
|
||||
public:
|
||||
Args args;
|
||||
template <class T> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
do {} while (detail::select(boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) );
|
||||
}
|
||||
};
|
||||
|
||||
// The code below is from Joel de Guzman, some name changes etc.
|
||||
// has been made.
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// while_composite
|
||||
//
|
||||
// This composite has the form:
|
||||
//
|
||||
// while_(condition)
|
||||
// [
|
||||
// statement
|
||||
// ]
|
||||
//
|
||||
// While the condition (an lambda_functor) evaluates to true, statement
|
||||
// (another lambda_functor) is executed. The result type of this is void.
|
||||
// Note the trailing underscore after while_.
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename CondT, typename DoT>
|
||||
struct while_composite {
|
||||
|
||||
typedef while_composite<CondT, DoT> self_t;
|
||||
|
||||
template <class SigArgs>
|
||||
struct sig { typedef void type; };
|
||||
|
||||
while_composite(CondT const& cond_, DoT const& do__)
|
||||
: cond(cond_), do_(do__) {}
|
||||
|
||||
template <class Ret, CALL_TEMPLATE_ARGS>
|
||||
Ret call(CALL_FORMAL_ARGS) const
|
||||
{
|
||||
while (cond.internal_call(CALL_ACTUAL_ARGS))
|
||||
do_.internal_call(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
|
||||
CondT cond;
|
||||
DoT do_;
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CondT>
|
||||
struct while_gen {
|
||||
|
||||
while_gen(CondT const& cond_)
|
||||
: cond(cond_) {}
|
||||
|
||||
template <typename DoT>
|
||||
lambda_functor<while_composite<
|
||||
typename as_lambda_functor<CondT>::type,
|
||||
typename as_lambda_functor<DoT>::type> >
|
||||
operator[](DoT const& do_) const
|
||||
{
|
||||
typedef while_composite<
|
||||
typename as_lambda_functor<CondT>::type,
|
||||
typename as_lambda_functor<DoT>::type>
|
||||
result;
|
||||
|
||||
return result(
|
||||
to_lambda_functor(cond),
|
||||
to_lambda_functor(do_));
|
||||
}
|
||||
|
||||
CondT cond;
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename CondT>
|
||||
inline while_gen<CondT>
|
||||
while_(CondT const& cond)
|
||||
{
|
||||
return while_gen<CondT>(cond);
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// do_composite
|
||||
//
|
||||
// This composite has the form:
|
||||
//
|
||||
// do_
|
||||
// [
|
||||
// statement
|
||||
// ]
|
||||
// .while_(condition)
|
||||
//
|
||||
// While the condition (an lambda_functor) evaluates to true, statement
|
||||
// (another lambda_functor) is executed. The statement is executed at least
|
||||
// once. The result type of this is void. Note the trailing
|
||||
// underscore after do_ and the leading dot and the trailing
|
||||
// underscore before and after .while_.
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename DoT, typename CondT>
|
||||
struct do_composite {
|
||||
|
||||
typedef do_composite<DoT, CondT> self_t;
|
||||
|
||||
template <class SigArgs>
|
||||
struct sig { typedef void type; };
|
||||
|
||||
do_composite(DoT const& do__, CondT const& cond_)
|
||||
: do_(do__), cond(cond_) {}
|
||||
|
||||
template <class Ret, CALL_TEMPLATE_ARGS>
|
||||
Ret call(CALL_FORMAL_ARGS) const
|
||||
{
|
||||
do
|
||||
do_.internal_call(CALL_ACTUAL_ARGS);
|
||||
while (cond.internal_call(CALL_ACTUAL_ARGS));
|
||||
}
|
||||
|
||||
DoT do_;
|
||||
CondT cond;
|
||||
};
|
||||
|
||||
////////////////////////////////////
|
||||
template <typename DoT>
|
||||
struct do_gen2 {
|
||||
|
||||
do_gen2(DoT const& do__)
|
||||
: do_(do__) {}
|
||||
|
||||
template <typename CondT>
|
||||
lambda_functor<do_composite<
|
||||
typename as_lambda_functor<DoT>::type,
|
||||
typename as_lambda_functor<CondT>::type> >
|
||||
while_(CondT const& cond) const
|
||||
{
|
||||
typedef do_composite<
|
||||
typename as_lambda_functor<DoT>::type,
|
||||
typename as_lambda_functor<CondT>::type>
|
||||
result;
|
||||
|
||||
return result(
|
||||
to_lambda_functor(do_),
|
||||
to_lambda_functor(cond));
|
||||
}
|
||||
|
||||
DoT do_;
|
||||
};
|
||||
|
||||
////////////////////////////////////
|
||||
struct do_gen {
|
||||
|
||||
template <typename DoT>
|
||||
do_gen2<DoT>
|
||||
operator[](DoT const& do_) const
|
||||
{
|
||||
return do_gen2<DoT>(do_);
|
||||
}
|
||||
};
|
||||
|
||||
do_gen const do_ = do_gen();
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// for_composite
|
||||
//
|
||||
// This statement has the form:
|
||||
//
|
||||
// for_(init, condition, step)
|
||||
// [
|
||||
// statement
|
||||
// ]
|
||||
//
|
||||
// Where init, condition, step and statement are all lambda_functors. init
|
||||
// is executed once before entering the for-loop. The for-loop
|
||||
// exits once condition evaluates to false. At each loop iteration,
|
||||
// step and statement is called. The result of this statement is
|
||||
// void. Note the trailing underscore after for_.
|
||||
//
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
template <typename InitT, typename CondT, typename StepT, typename DoT>
|
||||
struct for_composite {
|
||||
|
||||
template <class SigArgs>
|
||||
struct sig { typedef void type; };
|
||||
|
||||
for_composite(
|
||||
InitT const& init_,
|
||||
CondT const& cond_,
|
||||
StepT const& step_,
|
||||
DoT const& do__)
|
||||
: init(init_), cond(cond_), step(step_), do_(do__) {}
|
||||
|
||||
template <class Ret, CALL_TEMPLATE_ARGS>
|
||||
Ret
|
||||
call(CALL_FORMAL_ARGS) const
|
||||
{
|
||||
for (init.internal_call(CALL_ACTUAL_ARGS); cond.internal_call(CALL_ACTUAL_ARGS); step.internal_call(CALL_ACTUAL_ARGS))
|
||||
do_.internal_call(CALL_ACTUAL_ARGS);
|
||||
}
|
||||
|
||||
InitT init; CondT cond; StepT step; DoT do_; // lambda_functors
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename InitT, typename CondT, typename StepT>
|
||||
struct for_gen {
|
||||
|
||||
for_gen(
|
||||
InitT const& init_,
|
||||
CondT const& cond_,
|
||||
StepT const& step_)
|
||||
: init(init_), cond(cond_), step(step_) {}
|
||||
|
||||
template <typename DoT>
|
||||
lambda_functor<for_composite<
|
||||
typename as_lambda_functor<InitT>::type,
|
||||
typename as_lambda_functor<CondT>::type,
|
||||
typename as_lambda_functor<StepT>::type,
|
||||
typename as_lambda_functor<DoT>::type> >
|
||||
operator[](DoT const& do_) const
|
||||
{
|
||||
typedef for_composite<
|
||||
typename as_lambda_functor<InitT>::type,
|
||||
typename as_lambda_functor<CondT>::type,
|
||||
typename as_lambda_functor<StepT>::type,
|
||||
typename as_lambda_functor<DoT>::type>
|
||||
result;
|
||||
|
||||
return result(
|
||||
to_lambda_functor(init),
|
||||
to_lambda_functor(cond),
|
||||
to_lambda_functor(step),
|
||||
to_lambda_functor(do_));
|
||||
}
|
||||
|
||||
InitT init; CondT cond; StepT step;
|
||||
};
|
||||
|
||||
//////////////////////////////////
|
||||
template <typename InitT, typename CondT, typename StepT>
|
||||
inline for_gen<InitT, CondT, StepT>
|
||||
for_(InitT const& init, CondT const& cond, StepT const& step)
|
||||
{
|
||||
return for_gen<InitT, CondT, StepT>(init, cond, step);
|
||||
}
|
||||
|
||||
} // lambda
|
||||
} // boost
|
||||
|
||||
#endif // BOOST_LAMBDA_LOOPS_HPP
|
||||
119
include/boost/lambda/numeric.hpp
Normal file
119
include/boost/lambda/numeric.hpp
Normal file
@@ -0,0 +1,119 @@
|
||||
// -- numeric.hpp -- Boost Lambda Library -----------------------------------
|
||||
// Copyright (C) 2002 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2002 Gary Powell (gwpowell@hotmail.com)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see http://www.boost.org
|
||||
|
||||
#ifndef BOOST_LAMBDA_NUMERIC_HPP
|
||||
#define BOOST_LAMBDA_NUMERIC_HPP
|
||||
|
||||
#include "boost/lambda/core.hpp"
|
||||
|
||||
#include <numeric>
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
namespace ll {
|
||||
|
||||
// accumulate ---------------------------------
|
||||
|
||||
struct accumulate {
|
||||
|
||||
template <class Args>
|
||||
struct sig {
|
||||
typedef typename boost::remove_const<
|
||||
typename boost::tuples::element<3, Args>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
template <class A, class B, class C>
|
||||
C
|
||||
operator()(A a, B b, C c) const
|
||||
{ return ::std::accumulate(a, b, c); }
|
||||
|
||||
template <class A, class B, class C, class D>
|
||||
C
|
||||
operator()(A a, B b, C c, D d) const
|
||||
{ return ::std::accumulate(a, b, c, d); }
|
||||
};
|
||||
|
||||
// inner_product ---------------------------------
|
||||
|
||||
struct inner_product {
|
||||
|
||||
template <class Args>
|
||||
struct sig {
|
||||
typedef typename boost::remove_const<
|
||||
typename boost::tuples::element<4, Args>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
template <class A, class B, class C, class D>
|
||||
D
|
||||
operator()(A a, B b, C c, D d) const
|
||||
{ return ::std::inner_product(a, b, c, d); }
|
||||
|
||||
template <class A, class B, class C, class D, class E, class F>
|
||||
D
|
||||
operator()(A a, B b, C c, D d, E e, F f) const
|
||||
{ return ::std::inner_product(a, b, c, d, e, f); }
|
||||
};
|
||||
|
||||
|
||||
// partial_sum ---------------------------------
|
||||
|
||||
struct partial_sum {
|
||||
|
||||
template <class Args>
|
||||
struct sig {
|
||||
typedef typename boost::remove_const<
|
||||
typename boost::tuples::element<3, Args>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
template <class A, class B, class C>
|
||||
C
|
||||
operator()(A a, B b, C c) const
|
||||
{ return ::std::partial_sum(a, b, c); }
|
||||
|
||||
template <class A, class B, class C, class D>
|
||||
C
|
||||
operator()(A a, B b, C c, D d) const
|
||||
{ return ::std::partial_sum(a, b, c, d); }
|
||||
};
|
||||
|
||||
// adjacent_difference ---------------------------------
|
||||
|
||||
struct adjacent_difference {
|
||||
|
||||
template <class Args>
|
||||
struct sig {
|
||||
typedef typename boost::remove_const<
|
||||
typename boost::tuples::element<3, Args>::type
|
||||
>::type type;
|
||||
};
|
||||
|
||||
template <class A, class B, class C>
|
||||
C
|
||||
operator()(A a, B b, C c) const
|
||||
{ return ::std::adjacent_difference(a, b, c); }
|
||||
|
||||
template <class A, class B, class C, class D>
|
||||
C
|
||||
operator()(A a, B b, C c, D d) const
|
||||
{ return ::std::adjacent_difference(a, b, c, d); }
|
||||
};
|
||||
|
||||
} // end of ll namespace
|
||||
|
||||
} // end of lambda namespace
|
||||
} // end of boost namespace
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
508
include/boost/lambda/switch.hpp
Normal file
508
include/boost/lambda/switch.hpp
Normal file
@@ -0,0 +1,508 @@
|
||||
// Boost Lambda Library -- switch.hpp -----------------------------------
|
||||
//
|
||||
// Copyright (C) 2000 Gary Powell (powellg@amazon.com)
|
||||
// Copyright (C) 1999, 2000 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// --------------------------------------------------------------------------
|
||||
|
||||
#if !defined(BOOST_LAMBDA_SWITCH_HPP)
|
||||
#define BOOST_LAMBDA_SWITCH_HPP
|
||||
|
||||
#include "boost/lambda/core.hpp"
|
||||
#include "boost/lambda/detail/control_constructs_common.hpp"
|
||||
|
||||
#include "boost/preprocessor/enum_shifted_params.hpp"
|
||||
#include "boost/preprocessor/repeat_2nd.hpp"
|
||||
#include "boost/preprocessor/tuple.hpp"
|
||||
|
||||
namespace boost {
|
||||
namespace lambda {
|
||||
|
||||
// Switch actions
|
||||
template <int N, class Switch1 = null_type, class Switch2 = null_type,
|
||||
class Switch3 = null_type, class Switch4 = null_type,
|
||||
class Switch5 = null_type, class Switch6 = null_type,
|
||||
class Switch7 = null_type, class Switch8 = null_type,
|
||||
class Switch9 = null_type>
|
||||
struct switch_action {};
|
||||
|
||||
|
||||
namespace detail {
|
||||
|
||||
// templates to represent special lambda functors for the cases in
|
||||
// switch statements
|
||||
|
||||
template <int Value> struct case_label {};
|
||||
struct default_label {};
|
||||
|
||||
template<class Type> struct switch_case_tag {};
|
||||
|
||||
// a normal case is represented as:
|
||||
// tagged_lambda_functor<switch_case_tag<case_label<N> > >, LambdaFunctor>
|
||||
|
||||
// the default case as:
|
||||
// tagged_lambda_functor<switch_case_tag<default_label> >, LambdaFunctor>
|
||||
|
||||
|
||||
} // end detail
|
||||
|
||||
|
||||
/// create switch_case_tag tagged_lambda_functors
|
||||
template <int CaseValue, class Arg>
|
||||
inline const
|
||||
tagged_lambda_functor<
|
||||
detail::switch_case_tag<detail::case_label<CaseValue> >,
|
||||
lambda_functor<Arg>
|
||||
>
|
||||
case_statement(const lambda_functor<Arg>& a) {
|
||||
return
|
||||
tagged_lambda_functor<
|
||||
detail::switch_case_tag<detail::case_label<CaseValue> >,
|
||||
lambda_functor<Arg>
|
||||
>(a);
|
||||
}
|
||||
|
||||
// No case body case.
|
||||
template <int CaseValue>
|
||||
inline const
|
||||
tagged_lambda_functor<
|
||||
detail::switch_case_tag<detail::case_label<CaseValue> >,
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
do_nothing_action,
|
||||
null_type
|
||||
>
|
||||
>
|
||||
>
|
||||
case_statement() {
|
||||
return
|
||||
tagged_lambda_functor<
|
||||
detail::switch_case_tag<detail::case_label<CaseValue> >,
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
do_nothing_action,
|
||||
null_type
|
||||
>
|
||||
>
|
||||
> () ;
|
||||
}
|
||||
|
||||
// default label
|
||||
template <class Arg>
|
||||
inline const
|
||||
tagged_lambda_functor<
|
||||
detail::switch_case_tag<detail::default_label>,
|
||||
lambda_functor<Arg>
|
||||
>
|
||||
default_statement(const lambda_functor<Arg>& a) {
|
||||
return
|
||||
tagged_lambda_functor<
|
||||
detail::switch_case_tag<detail::default_label>,
|
||||
lambda_functor<Arg>
|
||||
>(a);
|
||||
}
|
||||
|
||||
// default lable, no case body case.
|
||||
inline const
|
||||
tagged_lambda_functor<
|
||||
detail::switch_case_tag<detail::default_label>,
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
do_nothing_action,
|
||||
null_type
|
||||
>
|
||||
>
|
||||
>
|
||||
default_statement() {
|
||||
return
|
||||
lambda_functor_base<
|
||||
do_nothing_action,
|
||||
null_type
|
||||
> () ;
|
||||
}
|
||||
|
||||
|
||||
// Specializations for lambda_functor_base of case_statement -----------------
|
||||
|
||||
// 0 case type:
|
||||
// useless (just the condition part) but provided for completeness.
|
||||
template<class Args>
|
||||
class
|
||||
lambda_functor_base<
|
||||
switch_action<1>,
|
||||
Args
|
||||
>
|
||||
{
|
||||
public:
|
||||
Args args;
|
||||
template <class SigArgs> struct sig { typedef void type; };
|
||||
public:
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
template<class RET, CALL_TEMPLATE_ARGS>
|
||||
RET call(CALL_FORMAL_ARGS) const {
|
||||
detail::select(::boost::tuples::get<1>(args), CALL_ACTUAL_ARGS);
|
||||
}
|
||||
};
|
||||
|
||||
// 1 case type:
|
||||
// template<class Args, int Case1>
|
||||
// class
|
||||
// lambda_functor_base<
|
||||
// action<
|
||||
// 2,
|
||||
// return_void_action<switch_action<detail::case_label<Case1> > >
|
||||
// >,
|
||||
// Args
|
||||
// >
|
||||
// {
|
||||
// Args args;
|
||||
// public:
|
||||
// explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
// template<class RET, class A, class B, class C>
|
||||
// RET call(A& a, B& b, C& c) const {
|
||||
// switch( detail::select(::boost::tuples::get<0>(args), a, b, c) )
|
||||
// {
|
||||
// case Case1:
|
||||
// detail::select(::boost::tuples::get<1>(args), a, b, c);
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// };
|
||||
|
||||
// switch with default being the sole label - doesn't make much sense but
|
||||
// it is there for completeness
|
||||
// template<class Args>
|
||||
// class
|
||||
// lambda_functor_base<
|
||||
// action<
|
||||
// 2,
|
||||
// return_void_action<switch_action<detail::default_label> >
|
||||
// >,
|
||||
// Args
|
||||
// >
|
||||
// {
|
||||
// Args args;
|
||||
// public:
|
||||
// explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
//
|
||||
// template<class RET, class A, class B, class C>
|
||||
// RET call(A& a, B& b, C& c) const {
|
||||
// switch( detail::select(::boost::tuples::get<0>(args), a, b, c) )
|
||||
// {
|
||||
// default:
|
||||
// detail::select(::boost::tuples::get<1>(args), a, b, c);
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// };
|
||||
|
||||
|
||||
|
||||
// // 2 case type:
|
||||
// The different specializations are generated with Vesa Karvonen's
|
||||
// preprocessor library.
|
||||
|
||||
// This is just a comment to show what the generated classes look like
|
||||
|
||||
// template<class Args, int Case1, int Case2>
|
||||
// class
|
||||
// lambda_functor_base<
|
||||
// action<3,
|
||||
// return_void_action<
|
||||
// switch_action<
|
||||
// detail::case_label<Case1>,
|
||||
// detail::case_label<Case2>
|
||||
// >
|
||||
// >
|
||||
// >,
|
||||
// Args
|
||||
// >
|
||||
// {
|
||||
// Args args;
|
||||
// public:
|
||||
// explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
// template<class RET, class A, class B, class C>
|
||||
// RET call(A& a, B& b, C& c) const {
|
||||
// switch( detail::select(::boost::tuples::get<0>(args), a, b, c) )
|
||||
// {
|
||||
// case Case1:
|
||||
// detail::select(::boost::tuples::get<1>(args), a, b, c);
|
||||
// break;
|
||||
// case Case2:
|
||||
// detail::select(::boost::tuples::get<2>(args), a, b, c);
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// };
|
||||
|
||||
// template<class Args, int Case1>
|
||||
// class
|
||||
// lambda_functor_base<
|
||||
// action<3,
|
||||
// return_void_action<
|
||||
// switch_action<
|
||||
// detail::case_label<Case1>,
|
||||
// detail::default_label
|
||||
// >
|
||||
// >
|
||||
// >,
|
||||
// Args
|
||||
// >
|
||||
// {
|
||||
// Args args;
|
||||
// public:
|
||||
// explicit lambda_functor_base(const Args& a) : args(a) {}
|
||||
|
||||
// template<class RET, class A, class B, class C>
|
||||
// RET call(A& a, B& b, C& c) const {
|
||||
// switch( detail::select(::boost::tuples::get<0>(args), a, b, c) )
|
||||
// {
|
||||
// case Case1:
|
||||
// detail::select(::boost::tuples::get<1>(args), a, b, c);
|
||||
// break;
|
||||
// default:
|
||||
// detail::select(::boost::tuples::get<2>(args), a, b, c);
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// };
|
||||
// -------------------------
|
||||
|
||||
// Some helper preprocessor macros ---------------------------------
|
||||
|
||||
// BOOST_LAMBDA_A_I_LIST(N, X) is a list of form X0, X1, ..., XN
|
||||
// BOOST_LAMBDA_A_I_B_LIST(N, X, Y) is a list of form X0 Y, X1 Y, ..., XN Y
|
||||
|
||||
#define BOOST_LAMBDA_A_I(z, i, A) \
|
||||
BOOST_PP_COMMA_IF(i) BOOST_PP_CAT(A,i)
|
||||
|
||||
#define BOOST_LAMBDA_A_I_B(z, i, T) \
|
||||
BOOST_PP_COMMA_IF(i) BOOST_PP_CAT(BOOST_PP_TUPLE_ELEM(2,0,T),i) BOOST_PP_TUPLE_ELEM(2,1,T)
|
||||
|
||||
#define BOOST_LAMBDA_A_I_LIST(i, A) \
|
||||
BOOST_PP_REPEAT(i,BOOST_LAMBDA_A_I, A)
|
||||
|
||||
#define BOOST_LAMBDA_A_I_B_LIST(i, A, B) \
|
||||
BOOST_PP_REPEAT(i,BOOST_LAMBDA_A_I_B, (A,B))
|
||||
|
||||
|
||||
// Switch related macros -------------------------------------------
|
||||
#define BOOST_LAMBDA_SWITCH_CASE_BLOCK(z, N, A) \
|
||||
case Case##N: \
|
||||
detail::select(::boost::tuples::get<BOOST_PP_INC(N)>(args), CALL_ACTUAL_ARGS); \
|
||||
break;
|
||||
|
||||
#define BOOST_LAMBDA_SWITCH_CASE_BLOCK_LIST(N) \
|
||||
BOOST_PP_REPEAT(N, BOOST_LAMBDA_SWITCH_CASE_BLOCK, FOO)
|
||||
// 2 case type:
|
||||
|
||||
#define BOOST_LAMBDA_SWITCH_NO_DEFAULT_CASE(N) \
|
||||
template<class Args, BOOST_LAMBDA_A_I_LIST(N, int Case)> \
|
||||
class \
|
||||
lambda_functor_base< \
|
||||
switch_action<BOOST_PP_INC(N), \
|
||||
BOOST_LAMBDA_A_I_B_LIST(N, detail::case_label<Case,>) \
|
||||
>, \
|
||||
Args \
|
||||
> \
|
||||
{ \
|
||||
public: \
|
||||
Args args; \
|
||||
template <class SigArgs> struct sig { typedef void type; }; \
|
||||
public: \
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {} \
|
||||
\
|
||||
template<class RET, CALL_TEMPLATE_ARGS> \
|
||||
RET call(CALL_FORMAL_ARGS) const { \
|
||||
switch( detail::select(::boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) ) \
|
||||
{ \
|
||||
BOOST_LAMBDA_SWITCH_CASE_BLOCK_LIST(N) \
|
||||
} \
|
||||
} \
|
||||
};
|
||||
|
||||
|
||||
|
||||
#define BOOST_LAMBDA_SWITCH_WITH_DEFAULT_CASE(N) \
|
||||
template< \
|
||||
class Args BOOST_PP_COMMA_IF(BOOST_PP_DEC(N)) \
|
||||
BOOST_LAMBDA_A_I_LIST(BOOST_PP_DEC(N), int Case) \
|
||||
> \
|
||||
class \
|
||||
lambda_functor_base< \
|
||||
switch_action<BOOST_PP_INC(N), \
|
||||
BOOST_LAMBDA_A_I_B_LIST(BOOST_PP_DEC(N), \
|
||||
detail::case_label<Case, >) \
|
||||
BOOST_PP_COMMA_IF(BOOST_PP_DEC(N)) \
|
||||
detail::default_label \
|
||||
>, \
|
||||
Args \
|
||||
> \
|
||||
{ \
|
||||
public: \
|
||||
Args args; \
|
||||
template <class SigArgs> struct sig { typedef void type; }; \
|
||||
public: \
|
||||
explicit lambda_functor_base(const Args& a) : args(a) {} \
|
||||
\
|
||||
template<class RET, CALL_TEMPLATE_ARGS> \
|
||||
RET call(CALL_FORMAL_ARGS) const { \
|
||||
switch( detail::select(::boost::tuples::get<0>(args), CALL_ACTUAL_ARGS) ) \
|
||||
{ \
|
||||
BOOST_LAMBDA_SWITCH_CASE_BLOCK_LIST(BOOST_PP_DEC(N)) \
|
||||
default: \
|
||||
detail::select(::boost::tuples::get<N>(args), CALL_ACTUAL_ARGS); \
|
||||
break; \
|
||||
} \
|
||||
} \
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// switch_statement bind functions -------------------------------------
|
||||
|
||||
// The zero argument case, for completeness sake
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
do_nothing_action,
|
||||
null_type
|
||||
>
|
||||
>
|
||||
switch_statement() {
|
||||
return
|
||||
lambda_functor_base<
|
||||
do_nothing_action,
|
||||
null_type
|
||||
>
|
||||
();
|
||||
}
|
||||
|
||||
// 1 argument case, this is useless as well, just the condition part
|
||||
template <class TestArg>
|
||||
inline const
|
||||
lambda_functor<
|
||||
lambda_functor_base<
|
||||
switch_action<1>,
|
||||
tuple<lambda_functor<TestArg> >
|
||||
>
|
||||
>
|
||||
switch_statement(const lambda_functor<TestArg>& a1) {
|
||||
return
|
||||
lambda_functor_base<
|
||||
switch_action<1>,
|
||||
tuple< lambda_functor<TestArg> >
|
||||
>
|
||||
( tuple<lambda_functor<TestArg> >(a1));
|
||||
}
|
||||
|
||||
|
||||
#define HELPER(z, N, FOO) \
|
||||
BOOST_PP_COMMA_IF(N) \
|
||||
BOOST_PP_CAT( \
|
||||
const tagged_lambda_functor<detail::switch_case_tag<TagData, \
|
||||
N>) \
|
||||
BOOST_PP_COMMA() Arg##N>& a##N
|
||||
|
||||
#define HELPER_LIST(N) BOOST_PP_REPEAT(N, HELPER, FOO)
|
||||
|
||||
|
||||
#define BOOST_LAMBDA_SWITCH_STATEMENT(N) \
|
||||
template <class TestArg, \
|
||||
BOOST_LAMBDA_A_I_LIST(N, class TagData), \
|
||||
BOOST_LAMBDA_A_I_LIST(N, class Arg)> \
|
||||
inline const \
|
||||
lambda_functor< \
|
||||
lambda_functor_base< \
|
||||
switch_action<BOOST_PP_INC(N), \
|
||||
BOOST_LAMBDA_A_I_LIST(N, TagData) \
|
||||
>, \
|
||||
tuple<lambda_functor<TestArg>, BOOST_LAMBDA_A_I_LIST(N, Arg)> \
|
||||
> \
|
||||
> \
|
||||
switch_statement( \
|
||||
const lambda_functor<TestArg>& ta, \
|
||||
HELPER_LIST(N) \
|
||||
) \
|
||||
{ \
|
||||
return \
|
||||
lambda_functor_base< \
|
||||
switch_action<BOOST_PP_INC(N), \
|
||||
BOOST_LAMBDA_A_I_LIST(N, TagData) \
|
||||
>, \
|
||||
tuple<lambda_functor<TestArg>, BOOST_LAMBDA_A_I_LIST(N, Arg)> \
|
||||
> \
|
||||
( tuple<lambda_functor<TestArg>, BOOST_LAMBDA_A_I_LIST(N, Arg)> \
|
||||
(ta, BOOST_LAMBDA_A_I_LIST(N, a) )); \
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
// Here's the actual generation
|
||||
|
||||
#define BOOST_LAMBDA_SWITCH(N) \
|
||||
BOOST_LAMBDA_SWITCH_NO_DEFAULT_CASE(N) \
|
||||
BOOST_LAMBDA_SWITCH_WITH_DEFAULT_CASE(N)
|
||||
|
||||
// Use this to avoid case 0, these macros work only from case 1 upwards
|
||||
#define BOOST_LAMBDA_SWITCH_HELPER(z, N, A) \
|
||||
BOOST_LAMBDA_SWITCH( BOOST_PP_INC(N) )
|
||||
|
||||
// Use this to avoid cases 0 and 1, these macros work only from case 2 upwards
|
||||
#define BOOST_LAMBDA_SWITCH_STATEMENT_HELPER(z, N, A) \
|
||||
BOOST_LAMBDA_SWITCH_STATEMENT(BOOST_PP_INC(N))
|
||||
|
||||
#ifdef BOOST_MSVC
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4065)
|
||||
#endif
|
||||
|
||||
// up to 9 cases supported (counting default:)
|
||||
BOOST_PP_REPEAT_2ND(9,BOOST_LAMBDA_SWITCH_HELPER,FOO)
|
||||
BOOST_PP_REPEAT_2ND(9,BOOST_LAMBDA_SWITCH_STATEMENT_HELPER,FOO)
|
||||
|
||||
#ifdef BOOST_MSVC
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
} // namespace lambda
|
||||
} // namespace boost
|
||||
|
||||
|
||||
#undef HELPER
|
||||
#undef HELPER_LIST
|
||||
|
||||
#undef BOOST_LAMBDA_SWITCH_HELPER
|
||||
#undef BOOST_LAMBDA_SWITCH
|
||||
#undef BOOST_LAMBDA_SWITCH_NO_DEFAULT_CASE
|
||||
#undef BOOST_LAMBDA_SWITCH_WITH_DEFAULT_CASE
|
||||
|
||||
#undef BOOST_LAMBDA_SWITCH_CASE_BLOCK
|
||||
#undef BOOST_LAMBDA_SWITCH_CASE_BLOCK_LIST
|
||||
|
||||
#undef BOOST_LAMBDA_SWITCH_STATEMENT
|
||||
#undef BOOST_LAMBDA_SWITCH_STATEMENT_HELPER
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -3,6 +3,10 @@
|
||||
<meta http-equiv="refresh" content="0; URL=../../doc/html/lambda.html">
|
||||
</head>
|
||||
<body>
|
||||
Automatic redirection failed, please go to <a href="../../doc/html/lambda.html">www.boost.org/doc/html/lambda.html</a>
|
||||
Automatic redirection failed, please go to <a href="../../doc/html/lambda.html">www.boost.org/doc/html/lambda.html</a> <hr>
|
||||
<p>© Copyright Beman Dawes, 2001</p>
|
||||
<p>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">www.boost.org/LICENSE_1_0.txt</a>)</p>
|
||||
</body>
|
||||
</html>
|
||||
16
meta/libraries.json
Normal file
16
meta/libraries.json
Normal file
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"key": "lambda",
|
||||
"name": "Lambda",
|
||||
"authors": [
|
||||
"Jaakko Järvi",
|
||||
"Gary Powell"
|
||||
],
|
||||
"description": "Define small unnamed function objects at the actual call site, and more.",
|
||||
"category": [
|
||||
"Function-objects"
|
||||
],
|
||||
"maintainers": [
|
||||
"Jaakko Jarvi <jarvi -at- cs.tamu.edu>"
|
||||
],
|
||||
"cxxstd": "03"
|
||||
}
|
||||
11
test/CMakeLists.txt
Normal file
11
test/CMakeLists.txt
Normal file
@@ -0,0 +1,11 @@
|
||||
# Copyright 2018, 2019 Peter Dimov
|
||||
# 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
|
||||
|
||||
include(BoostTestJamfile OPTIONAL RESULT_VARIABLE HAVE_BOOST_TEST)
|
||||
|
||||
if(HAVE_BOOST_TEST)
|
||||
|
||||
boost_test_jamfile(FILE Jamfile LINK_LIBRARIES Boost::lambda Boost::core Boost::any Boost::function Boost::smart_ptr)
|
||||
|
||||
endif()
|
||||
79
test/Jamfile
79
test/Jamfile
@@ -1,59 +1,36 @@
|
||||
# Lambda library
|
||||
|
||||
# Copyright (C) 2001-2003 Jaakko Järvi
|
||||
# Copyright (C) 2001-2003 Jaakko J<EFBFBD>rvi
|
||||
|
||||
# Use, modification and distribution is subject to 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)
|
||||
# Use, modification and distribution is subject to 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)
|
||||
|
||||
# For more information, see http://www.boost.org/
|
||||
|
||||
import testing ;
|
||||
|
||||
subproject libs/lambda/test ;
|
||||
project : requirements <library>/boost/lambda//boost_lambda ;
|
||||
|
||||
# bring in rules for testing
|
||||
SEARCH on testing.jam = $(BOOST_BUILD_PATH) ;
|
||||
include testing.jam ;
|
||||
|
||||
# Make tests run by default.
|
||||
DEPENDS all : test ;
|
||||
|
||||
{
|
||||
# look in BOOST_ROOT for sources first, just in this Jamfile
|
||||
local SEARCH_SOURCE = $(BOOST_ROOT) $(SEARCH_SOURCE) ;
|
||||
|
||||
test-suite lambda
|
||||
:
|
||||
[ run libs/lambda/test/algorithm_test.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/bind_tests_simple.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/bind_tests_advanced.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/bind_tests_simple_f_refs.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/bll_and_function.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/cast_test.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/constructor_tests.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/control_structures.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/exception_test.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/extending_rt_traits.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/is_instance_of_test.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/member_pointer_test.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/operator_tests_simple.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/phoenix_control_structures.cpp : : : : ]
|
||||
|
||||
[ run libs/lambda/test/switch_construct.cpp : : : : ]
|
||||
;
|
||||
|
||||
}
|
||||
|
||||
run algorithm_test.cpp ;
|
||||
run bind_tests_advanced.cpp : : : <library>/boost/any//boost_any ;
|
||||
run bind_tests_simple.cpp ;
|
||||
run bind_tests_simple_f_refs.cpp ;
|
||||
run bll_and_function.cpp ;
|
||||
run cast_test.cpp ;
|
||||
run constructor_tests.cpp ;
|
||||
run control_structures.cpp ;
|
||||
run exception_test.cpp
|
||||
: : : <toolset>msvc-14.0,<variant>release:<build>no # crash with 8 catch blocks
|
||||
;
|
||||
run extending_rt_traits.cpp ;
|
||||
run is_instance_of_test.cpp ;
|
||||
run istreambuf_test.cpp ;
|
||||
run member_pointer_test.cpp ;
|
||||
run operator_tests_simple.cpp ;
|
||||
run phoenix_control_structures.cpp ;
|
||||
run result_of_tests.cpp ;
|
||||
run ret_test.cpp ;
|
||||
run rvalue_test.cpp ;
|
||||
run switch_construct.cpp ;
|
||||
link issue24_test.cpp ;
|
||||
|
||||
4
test/Makefile
Executable file → Normal file
4
test/Makefile
Executable file → Normal file
@@ -1,7 +1,7 @@
|
||||
BOOST = ../../..
|
||||
|
||||
CXX = gcc
|
||||
EXTRAFLAGS = -pedantic -Wno-long-long -ftemplate-depth-50
|
||||
CXX = g++
|
||||
EXTRAFLAGS = -pedantic -Wno-long-long -Wno-long-double -ftemplate-depth-50
|
||||
LIBS = -lstdc++
|
||||
|
||||
#CXX = KCC
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// bll_and_function.cpp - The Boost Lambda Library -----------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -11,7 +11,8 @@
|
||||
|
||||
// test using BLL and boost::function
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
#include "boost/lambda/bind.hpp"
|
||||
@@ -41,20 +42,14 @@ void test_foreach() {
|
||||
bind(ll::for_each(), _1, _1 + 20,
|
||||
protect((sum += _1))));
|
||||
|
||||
BOOST_TEST(sum == (199 + 1)/ 2 * 199);
|
||||
BOOST_CHECK(sum == (199 + 1)/ 2 * 199);
|
||||
}
|
||||
|
||||
// More tests needed (for all algorithms)
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
test_foreach();
|
||||
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
// bind_tests_advanced.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
// Copyright (C) 2010 Steven Watanabe
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
// accompanying file LICENSE_1_0.txt or copy at
|
||||
@@ -12,13 +13,17 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
#include "boost/lambda/bind.hpp"
|
||||
|
||||
|
||||
#include "boost/any.hpp"
|
||||
#include "boost/type_traits/is_reference.hpp"
|
||||
#include "boost/mpl/assert.hpp"
|
||||
#include "boost/mpl/if.hpp"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
@@ -27,7 +32,8 @@
|
||||
#include <algorithm>
|
||||
|
||||
|
||||
using namespace boost::lambda;
|
||||
using namespace boost::lambda;
|
||||
namespace bl = boost::lambda;
|
||||
|
||||
int sum_0() { return 0; }
|
||||
int sum_1(int a) { return a; }
|
||||
@@ -60,16 +66,16 @@ void test_nested_binds()
|
||||
bool condition;
|
||||
|
||||
condition = true;
|
||||
BOOST_TEST(bind(bind(&sum_or_product, _1), 1, 2)(condition)==3);
|
||||
BOOST_TEST(bind(bind(&sum_or_product, _1), _2, _3)(condition, j, k)==5);
|
||||
BOOST_CHECK(bind(bind(&sum_or_product, _1), 1, 2)(condition)==3);
|
||||
BOOST_CHECK(bind(bind(&sum_or_product, _1), _2, _3)(condition, j, k)==5);
|
||||
|
||||
condition = false;
|
||||
BOOST_TEST(bind(bind(&sum_or_product, _1), 1, 2)(condition)==2);
|
||||
BOOST_TEST(bind(bind(&sum_or_product, _1), _2, _3)(condition, j, k)==6);
|
||||
BOOST_CHECK(bind(bind(&sum_or_product, _1), 1, 2)(condition)==2);
|
||||
BOOST_CHECK(bind(bind(&sum_or_product, _1), _2, _3)(condition, j, k)==6);
|
||||
|
||||
|
||||
which_one wo;
|
||||
BOOST_TEST(bind(bind(bind(wo), _1), _2, _3)(condition, j, k)==6);
|
||||
BOOST_CHECK(bind(bind(bind(wo), _1), _2, _3)(condition, j, k)==6);
|
||||
|
||||
|
||||
return;
|
||||
@@ -91,7 +97,7 @@ int call_with_100(const F& f) {
|
||||
// This would result in;
|
||||
// bind(_1 + 1, _1)(make_const(100)) , which would be a compile time error
|
||||
|
||||
return bind(unlambda(f), _1)(make_const(100));
|
||||
return bl::bind(unlambda(f), _1)(make_const(100));
|
||||
|
||||
// for other functors than lambda functors, unlambda has no effect
|
||||
// (except for making them const)
|
||||
@@ -109,18 +115,44 @@ void test_unlambda() {
|
||||
|
||||
int i = 1;
|
||||
|
||||
BOOST_TEST(unlambda(_1 + _2)(i, i) == 2);
|
||||
BOOST_TEST(unlambda(++var(i))() == 2);
|
||||
BOOST_TEST(call_with_100(_1 + 1) == 101);
|
||||
BOOST_CHECK(unlambda(_1 + _2)(i, i) == 2);
|
||||
BOOST_CHECK(unlambda(++var(i))() == 2);
|
||||
BOOST_CHECK(call_with_100(_1 + 1) == 101);
|
||||
|
||||
|
||||
BOOST_TEST(call_with_101(_1 + 1) == 102);
|
||||
BOOST_CHECK(call_with_101(_1 + 1) == 102);
|
||||
|
||||
BOOST_TEST(call_with_100(bind(std_functor(std::bind1st(std::plus<int>(), 1)), _1)) == 101);
|
||||
#if defined(BOOST_NO_CXX11_HDR_FUNCTIONAL)
|
||||
|
||||
BOOST_CHECK(call_with_100(bl::bind(std_functor(std::bind1st(std::plus<int>(), 1)), _1)) == 101);
|
||||
|
||||
#elif BOOST_CXX_VERSION > 201703L
|
||||
|
||||
// In C++20, standard functors no longer have ::result_type
|
||||
BOOST_CHECK(call_with_100(bl::bind(std::bind(std::plus<int>(), 1, std::placeholders::_1), _1)) == 101);
|
||||
|
||||
#elif defined(BOOST_MSVC) && BOOST_MSVC < 1900
|
||||
|
||||
// Mysterious failures under msvc-12.0 and below
|
||||
|
||||
#else
|
||||
|
||||
BOOST_CHECK(call_with_100(bl::bind(std_functor(std::bind(std::plus<int>(), 1, std::placeholders::_1)), _1)) == 101);
|
||||
|
||||
#endif
|
||||
|
||||
#if BOOST_CXX_VERSION <= 201703L
|
||||
|
||||
// std_functor insturcts LL that the functor defines a result_type typedef
|
||||
// rather than a sig template.
|
||||
bind(std_functor(std::plus<int>()), _1, _2)(i, i);
|
||||
bl::bind(std_functor(std::plus<int>()), _1, _2)(i, i);
|
||||
|
||||
#else
|
||||
|
||||
// In C++20, standard functors no longer have ::result_type
|
||||
bl::bind(std::plus<int>(), _1, _2)(i, i);
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
@@ -200,7 +232,7 @@ void test_protect()
|
||||
bind(ll::for_each(), _1, _1 + 5,
|
||||
protect(sum += _1))
|
||||
);
|
||||
BOOST_TEST(sum == (1+15)*15/2);
|
||||
BOOST_CHECK(sum == (1+15)*15/2);
|
||||
|
||||
sum = 0;
|
||||
|
||||
@@ -208,17 +240,17 @@ void test_protect()
|
||||
bind(ll::for_each(), _1, _1 + 5,
|
||||
sum += 1 + protect(_1)) // add element count
|
||||
);
|
||||
BOOST_TEST(sum == (1+15)*15/2 + 15);
|
||||
BOOST_CHECK(sum == (1+15)*15/2 + 15);
|
||||
|
||||
(1 + protect(_1))(sum);
|
||||
|
||||
int k = 0;
|
||||
((k += constant(1)) += protect(constant(2)))();
|
||||
BOOST_TEST(k==1);
|
||||
BOOST_CHECK(k==1);
|
||||
|
||||
k = 0;
|
||||
((k += constant(1)) += protect(constant(2)))()();
|
||||
BOOST_TEST(k==3);
|
||||
BOOST_CHECK(k==3);
|
||||
|
||||
// note, the following doesn't work:
|
||||
|
||||
@@ -276,10 +308,10 @@ void test_lambda_functors_as_arguments_to_lambda_functors() {
|
||||
// sum_0() + 7, but rather
|
||||
// bind(sum_0) + 7, which results in another lambda functor
|
||||
// (lambda functor + int) and can be called again
|
||||
BOOST_TEST((_1 + _2)(bind(&sum_0), make_const(7))() == 7);
|
||||
BOOST_CHECK((_1 + _2)(bind(&sum_0), make_const(7))() == 7);
|
||||
|
||||
int i = 3, j = 12;
|
||||
BOOST_TEST((_1 - _2)(_2, _1)(i, j) == j - i);
|
||||
BOOST_CHECK((_1 - _2)(_2, _1)(i, j) == j - i);
|
||||
|
||||
// also, note that lambda functor are no special case for bind if received
|
||||
// as a parameter. In oder to be bindable, the functor must
|
||||
@@ -292,12 +324,12 @@ void test_lambda_functors_as_arguments_to_lambda_functors() {
|
||||
int a = 5, b = 6;
|
||||
|
||||
// Let type deduction find out the return type
|
||||
BOOST_TEST(bind(_1, _2, _3)(unlambda(_1 + _2), a, b) == 11);
|
||||
BOOST_CHECK(bind(_1, _2, _3)(unlambda(_1 + _2), a, b) == 11);
|
||||
|
||||
//specify it yourself:
|
||||
BOOST_TEST(bind(_1, _2, _3)(ret<int>(_1 + _2), a, b) == 11);
|
||||
BOOST_TEST(ret<int>(bind(_1, _2, _3))(_1 + _2, a, b) == 11);
|
||||
BOOST_TEST(bind<int>(_1, _2, _3)(_1 + _2, a, b) == 11);
|
||||
BOOST_CHECK(bind(_1, _2, _3)(ret<int>(_1 + _2), a, b) == 11);
|
||||
BOOST_CHECK(ret<int>(bind(_1, _2, _3))(_1 + _2, a, b) == 11);
|
||||
BOOST_CHECK(bind<int>(_1, _2, _3)(_1 + _2, a, b) == 11);
|
||||
|
||||
bind(_1,1.0)(_1+_1);
|
||||
return;
|
||||
@@ -310,10 +342,10 @@ void test_const_parameters() {
|
||||
// (_1 + _2)(1, 2); // this would fail,
|
||||
|
||||
// Either make arguments const:
|
||||
BOOST_TEST((_1 + _2)(make_const(1), make_const(2)) == 3);
|
||||
BOOST_CHECK((_1 + _2)(make_const(1), make_const(2)) == 3);
|
||||
|
||||
// Or use const_parameters:
|
||||
BOOST_TEST(const_parameters(_1 + _2)(1, 2) == 3);
|
||||
BOOST_CHECK(const_parameters(_1 + _2)(1, 2) == 3);
|
||||
|
||||
|
||||
|
||||
@@ -323,7 +355,7 @@ void test_rvalue_arguments()
|
||||
{
|
||||
// Not quite working yet.
|
||||
// Problems with visual 7.1
|
||||
// BOOST_TEST((_1 + _2)(1, 2) == 3);
|
||||
// BOOST_CHECK((_1 + _2)(1, 2) == 3);
|
||||
}
|
||||
|
||||
void test_break_const()
|
||||
@@ -348,10 +380,59 @@ void test_break_const()
|
||||
// OLD COMMENT: (_1 += _2)(i, 2) // fails, 2 is a non-const rvalue
|
||||
// OLD COMMENT: const_parameters(_1 += _2)(i, 2) // fails, side-effect to i
|
||||
break_const(_1 += _2)(i, 2); // ok
|
||||
BOOST_TEST(i == 3);
|
||||
BOOST_CHECK(i == 3);
|
||||
}
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
template<class T>
|
||||
struct func {
|
||||
template<class Args>
|
||||
struct sig {
|
||||
typedef typename boost::tuples::element<1, Args>::type arg1;
|
||||
// If the argument type is not the same as the expected type,
|
||||
// return void, which will cause an error. Note that we
|
||||
// can't just assert that the types are the same, because
|
||||
// both const and non-const versions can be instantiated
|
||||
// even though only one is ultimately used.
|
||||
typedef typename boost::mpl::if_<boost::is_same<arg1, T>,
|
||||
typename boost::remove_const<arg1>::type,
|
||||
void
|
||||
>::type type;
|
||||
};
|
||||
template<class U>
|
||||
U operator()(const U& arg) const {
|
||||
return arg;
|
||||
}
|
||||
};
|
||||
|
||||
void test_sig()
|
||||
{
|
||||
int i = 1;
|
||||
BOOST_CHECK(bind(func<int>(), 1)() == 1);
|
||||
BOOST_CHECK(bind(func<const int>(), _1)(static_cast<const int&>(i)) == 1);
|
||||
BOOST_CHECK(bind(func<int>(), _1)(i) == 1);
|
||||
}
|
||||
|
||||
class base {
|
||||
public:
|
||||
virtual int foo() = 0;
|
||||
};
|
||||
|
||||
class derived : public base {
|
||||
public:
|
||||
virtual int foo() {
|
||||
return 1;
|
||||
}
|
||||
};
|
||||
|
||||
void test_abstract()
|
||||
{
|
||||
derived d;
|
||||
base& b = d;
|
||||
BOOST_CHECK(bind(&base::foo, var(b))() == 1);
|
||||
BOOST_CHECK(bind(&base::foo, *_1)(&b) == 1);
|
||||
}
|
||||
|
||||
int main() {
|
||||
|
||||
test_nested_binds();
|
||||
test_unlambda();
|
||||
@@ -360,17 +441,7 @@ int test_main(int, char *[]) {
|
||||
test_const_parameters();
|
||||
test_rvalue_arguments();
|
||||
test_break_const();
|
||||
return 0;
|
||||
test_sig();
|
||||
test_abstract();
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// bind_tests_simple.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,15 +12,14 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/bind.hpp"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
|
||||
using namespace std;
|
||||
using namespace boost::lambda;
|
||||
using namespace boost::lambda;
|
||||
|
||||
|
||||
int sum_of_args_0() { return 0; }
|
||||
@@ -65,79 +64,96 @@ void test_member_functions()
|
||||
|
||||
|
||||
|
||||
BOOST_TEST(bind(&A::add, ref(a), _1)(i) == 11);
|
||||
BOOST_TEST(bind(&A::add, &a, _1)(i) == 11);
|
||||
BOOST_TEST(bind(&A::add, _1, 1)(a) == 11);
|
||||
BOOST_TEST(bind(&A::add, _1, 1)(make_const(&a)) == 11);
|
||||
BOOST_CHECK(bind(&A::add, ref(a), _1)(i) == 11);
|
||||
BOOST_CHECK(bind(&A::add, &a, _1)(i) == 11);
|
||||
BOOST_CHECK(bind(&A::add, _1, 1)(a) == 11);
|
||||
BOOST_CHECK(bind(&A::add, _1, 1)(make_const(&a)) == 11);
|
||||
|
||||
BOOST_TEST(bind(&A::add2, _1, 1, 1)(a) == 12);
|
||||
BOOST_TEST(bind(&A::add3, _1, 1, 1, 1)(a) == 13);
|
||||
BOOST_TEST(bind(&A::add4, _1, 1, 1, 1, 1)(a) == 14);
|
||||
BOOST_TEST(bind(&A::add5, _1, 1, 1, 1, 1, 1)(a) == 15);
|
||||
BOOST_TEST(bind(&A::add6, _1, 1, 1, 1, 1, 1, 1)(a) == 16);
|
||||
BOOST_TEST(bind(&A::add7, _1, 1, 1, 1, 1, 1, 1, 1)(a) == 17);
|
||||
BOOST_TEST(bind(&A::add8, _1, 1, 1, 1, 1, 1, 1, 1, 1)(a) == 18);
|
||||
BOOST_CHECK(bind(&A::add2, _1, 1, 1)(a) == 12);
|
||||
BOOST_CHECK(bind(&A::add3, _1, 1, 1, 1)(a) == 13);
|
||||
BOOST_CHECK(bind(&A::add4, _1, 1, 1, 1, 1)(a) == 14);
|
||||
BOOST_CHECK(bind(&A::add5, _1, 1, 1, 1, 1, 1)(a) == 15);
|
||||
BOOST_CHECK(bind(&A::add6, _1, 1, 1, 1, 1, 1, 1)(a) == 16);
|
||||
BOOST_CHECK(bind(&A::add7, _1, 1, 1, 1, 1, 1, 1, 1)(a) == 17);
|
||||
BOOST_CHECK(bind(&A::add8, _1, 1, 1, 1, 1, 1, 1, 1, 1)(a) == 18);
|
||||
|
||||
// This should fail, as lambda functors store arguments as const
|
||||
// bind(&A::add, a, _1);
|
||||
}
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
struct B {
|
||||
B(int n) : i(n) {};
|
||||
int i;
|
||||
};
|
||||
|
||||
void test_data_members()
|
||||
{
|
||||
using boost::ref;
|
||||
B b(10);
|
||||
BOOST_CHECK(bind(&B::i, ref(b))() == 10);
|
||||
BOOST_CHECK(bind(&B::i, b)() == 10);
|
||||
BOOST_CHECK(bind(&B::i, _1)(b) == 10);
|
||||
BOOST_CHECK(bind(&B::i, _1)(B(11)) == 11);
|
||||
bind(&B::i, ref(b))() = 1;
|
||||
BOOST_CHECK(b.i == 1);
|
||||
}
|
||||
|
||||
int main() {
|
||||
|
||||
int i = 1; int j = 2; int k = 3;
|
||||
int result;
|
||||
|
||||
// bind all parameters
|
||||
BOOST_TEST(bind(&sum_of_args_0)()==0);
|
||||
BOOST_TEST(bind(&sum_of_args_1, 1)()==1);
|
||||
BOOST_TEST(bind(&sum_of_args_2, 1, 2)()==3);
|
||||
BOOST_TEST(bind(&sum_of_args_3, 1, 2, 3)()==6);
|
||||
BOOST_TEST(bind(&sum_of_args_4, 1, 2, 3, 4)()==10);
|
||||
BOOST_TEST(bind(&sum_of_args_5, 1, 2, 3, 4, 5)()==15);
|
||||
BOOST_TEST(bind(&sum_of_args_6, 1, 2, 3, 4, 5, 6)()==21);
|
||||
BOOST_TEST(bind(&sum_of_args_7, 1, 2, 3, 4, 5, 6, 7)()==28);
|
||||
BOOST_TEST(bind(&sum_of_args_8, 1, 2, 3, 4, 5, 6, 7, 8)()==36);
|
||||
BOOST_TEST(bind(&sum_of_args_9, 1, 2, 3, 4, 5, 6, 7, 8, 9)()==45);
|
||||
BOOST_CHECK(bind(&sum_of_args_0)()==0);
|
||||
BOOST_CHECK(bind(&sum_of_args_1, 1)()==1);
|
||||
BOOST_CHECK(bind(&sum_of_args_2, 1, 2)()==3);
|
||||
BOOST_CHECK(bind(&sum_of_args_3, 1, 2, 3)()==6);
|
||||
BOOST_CHECK(bind(&sum_of_args_4, 1, 2, 3, 4)()==10);
|
||||
BOOST_CHECK(bind(&sum_of_args_5, 1, 2, 3, 4, 5)()==15);
|
||||
BOOST_CHECK(bind(&sum_of_args_6, 1, 2, 3, 4, 5, 6)()==21);
|
||||
BOOST_CHECK(bind(&sum_of_args_7, 1, 2, 3, 4, 5, 6, 7)()==28);
|
||||
BOOST_CHECK(bind(&sum_of_args_8, 1, 2, 3, 4, 5, 6, 7, 8)()==36);
|
||||
BOOST_CHECK(bind(&sum_of_args_9, 1, 2, 3, 4, 5, 6, 7, 8, 9)()==45);
|
||||
|
||||
// first parameter open
|
||||
BOOST_TEST(bind(&sum_of_args_0)()==0);
|
||||
BOOST_TEST(bind(&sum_of_args_1, _1)(i)==1);
|
||||
BOOST_TEST(bind(&sum_of_args_2, _1, 2)(i)==3);
|
||||
BOOST_TEST(bind(&sum_of_args_3, _1, 2, 3)(i)==6);
|
||||
BOOST_TEST(bind(&sum_of_args_4, _1, 2, 3, 4)(i)==10);
|
||||
BOOST_TEST(bind(&sum_of_args_5, _1, 2, 3, 4, 5)(i)==15);
|
||||
BOOST_TEST(bind(&sum_of_args_6, _1, 2, 3, 4, 5, 6)(i)==21);
|
||||
BOOST_TEST(bind(&sum_of_args_7, _1, 2, 3, 4, 5, 6, 7)(i)==28);
|
||||
BOOST_TEST(bind(&sum_of_args_8, _1, 2, 3, 4, 5, 6, 7, 8)(i)==36);
|
||||
BOOST_TEST(bind(&sum_of_args_9, _1, 2, 3, 4, 5, 6, 7, 8, 9)(i)==45);
|
||||
BOOST_CHECK(bind(&sum_of_args_0)()==0);
|
||||
BOOST_CHECK(bind(&sum_of_args_1, _1)(i)==1);
|
||||
BOOST_CHECK(bind(&sum_of_args_2, _1, 2)(i)==3);
|
||||
BOOST_CHECK(bind(&sum_of_args_3, _1, 2, 3)(i)==6);
|
||||
BOOST_CHECK(bind(&sum_of_args_4, _1, 2, 3, 4)(i)==10);
|
||||
BOOST_CHECK(bind(&sum_of_args_5, _1, 2, 3, 4, 5)(i)==15);
|
||||
BOOST_CHECK(bind(&sum_of_args_6, _1, 2, 3, 4, 5, 6)(i)==21);
|
||||
BOOST_CHECK(bind(&sum_of_args_7, _1, 2, 3, 4, 5, 6, 7)(i)==28);
|
||||
BOOST_CHECK(bind(&sum_of_args_8, _1, 2, 3, 4, 5, 6, 7, 8)(i)==36);
|
||||
BOOST_CHECK(bind(&sum_of_args_9, _1, 2, 3, 4, 5, 6, 7, 8, 9)(i)==45);
|
||||
|
||||
// two open arguments
|
||||
BOOST_TEST(bind(&sum_of_args_0)()==0);
|
||||
BOOST_TEST(bind(&sum_of_args_1, _1)(i)==1);
|
||||
BOOST_TEST(bind(&sum_of_args_2, _1, _2)(i, j)==3);
|
||||
BOOST_TEST(bind(&sum_of_args_3, _1, _2, 3)(i, j)==6);
|
||||
BOOST_TEST(bind(&sum_of_args_4, _1, _2, 3, 4)(i, j)==10);
|
||||
BOOST_TEST(bind(&sum_of_args_5, _1, _2, 3, 4, 5)(i, j)==15);
|
||||
BOOST_TEST(bind(&sum_of_args_6, _1, _2, 3, 4, 5, 6)(i, j)==21);
|
||||
BOOST_TEST(bind(&sum_of_args_7, _1, _2, 3, 4, 5, 6, 7)(i, j)==28);
|
||||
BOOST_TEST(bind(&sum_of_args_8, _1, _2, 3, 4, 5, 6, 7, 8)(i, j)==36);
|
||||
BOOST_TEST(bind(&sum_of_args_9, _1, _2, 3, 4, 5, 6, 7, 8, 9)(i, j)==45);
|
||||
BOOST_CHECK(bind(&sum_of_args_0)()==0);
|
||||
BOOST_CHECK(bind(&sum_of_args_1, _1)(i)==1);
|
||||
BOOST_CHECK(bind(&sum_of_args_2, _1, _2)(i, j)==3);
|
||||
BOOST_CHECK(bind(&sum_of_args_3, _1, _2, 3)(i, j)==6);
|
||||
BOOST_CHECK(bind(&sum_of_args_4, _1, _2, 3, 4)(i, j)==10);
|
||||
BOOST_CHECK(bind(&sum_of_args_5, _1, _2, 3, 4, 5)(i, j)==15);
|
||||
BOOST_CHECK(bind(&sum_of_args_6, _1, _2, 3, 4, 5, 6)(i, j)==21);
|
||||
BOOST_CHECK(bind(&sum_of_args_7, _1, _2, 3, 4, 5, 6, 7)(i, j)==28);
|
||||
BOOST_CHECK(bind(&sum_of_args_8, _1, _2, 3, 4, 5, 6, 7, 8)(i, j)==36);
|
||||
BOOST_CHECK(bind(&sum_of_args_9, _1, _2, 3, 4, 5, 6, 7, 8, 9)(i, j)==45);
|
||||
|
||||
// three open arguments
|
||||
BOOST_TEST(bind(&sum_of_args_0)()==0);
|
||||
BOOST_TEST(bind(&sum_of_args_1, _1)(i)==1);
|
||||
BOOST_TEST(bind(&sum_of_args_2, _1, _2)(i, j)==3);
|
||||
BOOST_TEST(bind(&sum_of_args_3, _1, _2, _3)(i, j, k)==6);
|
||||
BOOST_TEST(bind(&sum_of_args_4, _1, _2, _3, 4)(i, j, k)==10);
|
||||
BOOST_TEST(bind(&sum_of_args_5, _1, _2, _3, 4, 5)(i, j, k)==15);
|
||||
BOOST_TEST(bind(&sum_of_args_6, _1, _2, _3, 4, 5, 6)(i, j, k)==21);
|
||||
BOOST_TEST(bind(&sum_of_args_7, _1, _2, _3, 4, 5, 6, 7)(i, j, k)==28);
|
||||
BOOST_TEST(bind(&sum_of_args_8, _1, _2, _3, 4, 5, 6, 7, 8)(i, j, k)==36);
|
||||
BOOST_TEST(bind(&sum_of_args_9, _1, _2, _3, 4, 5, 6, 7, 8, 9)(i, j, k)==45);
|
||||
BOOST_CHECK(bind(&sum_of_args_0)()==0);
|
||||
BOOST_CHECK(bind(&sum_of_args_1, _1)(i)==1);
|
||||
BOOST_CHECK(bind(&sum_of_args_2, _1, _2)(i, j)==3);
|
||||
BOOST_CHECK(bind(&sum_of_args_3, _1, _2, _3)(i, j, k)==6);
|
||||
BOOST_CHECK(bind(&sum_of_args_4, _1, _2, _3, 4)(i, j, k)==10);
|
||||
BOOST_CHECK(bind(&sum_of_args_5, _1, _2, _3, 4, 5)(i, j, k)==15);
|
||||
BOOST_CHECK(bind(&sum_of_args_6, _1, _2, _3, 4, 5, 6)(i, j, k)==21);
|
||||
BOOST_CHECK(bind(&sum_of_args_7, _1, _2, _3, 4, 5, 6, 7)(i, j, k)==28);
|
||||
BOOST_CHECK(bind(&sum_of_args_8, _1, _2, _3, 4, 5, 6, 7, 8)(i, j, k)==36);
|
||||
BOOST_CHECK(bind(&sum_of_args_9, _1, _2, _3, 4, 5, 6, 7, 8, 9)(i, j, k)==45);
|
||||
|
||||
// function compositions with bind
|
||||
BOOST_TEST(bind(&sum_of_args_3, bind(&sum_of_args_2, _1, 2), 2, 3)(i)==8);
|
||||
BOOST_TEST(
|
||||
BOOST_CHECK(bind(&sum_of_args_3, bind(&sum_of_args_2, _1, 2), 2, 3)(i)==8);
|
||||
BOOST_CHECK(
|
||||
bind(&sum_of_args_9,
|
||||
bind(&sum_of_args_0), // 0
|
||||
bind(&sum_of_args_1, _1), // 1
|
||||
@@ -163,10 +179,10 @@ int test_main(int, char *[]) {
|
||||
_3,
|
||||
4)
|
||||
)(i, j, k);
|
||||
BOOST_TEST(result == 12);
|
||||
BOOST_CHECK(result == 12);
|
||||
|
||||
test_member_functions();
|
||||
|
||||
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// bind_tests_simple.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,15 +12,14 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/bind.hpp"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
|
||||
using namespace std;
|
||||
using namespace boost::lambda;
|
||||
using namespace boost::lambda;
|
||||
|
||||
|
||||
int sum_of_args_0() { return 0; }
|
||||
@@ -50,72 +49,72 @@ void test_member_functions()
|
||||
A a(10);
|
||||
int i = 1;
|
||||
|
||||
BOOST_TEST(bind(&A::add, ref(a), _1)(i) == 11);
|
||||
BOOST_TEST(bind(&A::add, &a, _1)(i) == 11);
|
||||
BOOST_TEST(bind(&A::add, _1, 1)(a) == 11);
|
||||
BOOST_TEST(bind(&A::add, _1, 1)(make_const(&a)) == 11);
|
||||
BOOST_CHECK(bind(&A::add, ref(a), _1)(i) == 11);
|
||||
BOOST_CHECK(bind(&A::add, &a, _1)(i) == 11);
|
||||
BOOST_CHECK(bind(&A::add, _1, 1)(a) == 11);
|
||||
BOOST_CHECK(bind(&A::add, _1, 1)(make_const(&a)) == 11);
|
||||
|
||||
// This should fail, as lambda functors store arguments as const
|
||||
// bind(&A::add, a, _1);
|
||||
}
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
int i = 1; int j = 2; int k = 3;
|
||||
int result;
|
||||
|
||||
|
||||
// bind all parameters
|
||||
BOOST_TEST(bind(sum_of_args_0)()==0);
|
||||
BOOST_TEST(bind(sum_of_args_1, 1)()==1);
|
||||
BOOST_TEST(bind(sum_of_args_2, 1, 2)()==3);
|
||||
BOOST_TEST(bind(sum_of_args_3, 1, 2, 3)()==6);
|
||||
BOOST_TEST(bind(sum_of_args_4, 1, 2, 3, 4)()==10);
|
||||
BOOST_TEST(bind(sum_of_args_5, 1, 2, 3, 4, 5)()==15);
|
||||
BOOST_TEST(bind(sum_of_args_6, 1, 2, 3, 4, 5, 6)()==21);
|
||||
BOOST_TEST(bind(sum_of_args_7, 1, 2, 3, 4, 5, 6, 7)()==28);
|
||||
BOOST_TEST(bind(sum_of_args_8, 1, 2, 3, 4, 5, 6, 7, 8)()==36);
|
||||
BOOST_TEST(bind(sum_of_args_9, 1, 2, 3, 4, 5, 6, 7, 8, 9)()==45);
|
||||
BOOST_CHECK(bind(sum_of_args_0)()==0);
|
||||
BOOST_CHECK(bind(sum_of_args_1, 1)()==1);
|
||||
BOOST_CHECK(bind(sum_of_args_2, 1, 2)()==3);
|
||||
BOOST_CHECK(bind(sum_of_args_3, 1, 2, 3)()==6);
|
||||
BOOST_CHECK(bind(sum_of_args_4, 1, 2, 3, 4)()==10);
|
||||
BOOST_CHECK(bind(sum_of_args_5, 1, 2, 3, 4, 5)()==15);
|
||||
BOOST_CHECK(bind(sum_of_args_6, 1, 2, 3, 4, 5, 6)()==21);
|
||||
BOOST_CHECK(bind(sum_of_args_7, 1, 2, 3, 4, 5, 6, 7)()==28);
|
||||
BOOST_CHECK(bind(sum_of_args_8, 1, 2, 3, 4, 5, 6, 7, 8)()==36);
|
||||
BOOST_CHECK(bind(sum_of_args_9, 1, 2, 3, 4, 5, 6, 7, 8, 9)()==45);
|
||||
|
||||
// first parameter open
|
||||
BOOST_TEST(bind(sum_of_args_0)()==0);
|
||||
BOOST_TEST(bind(sum_of_args_1, _1)(i)==1);
|
||||
BOOST_TEST(bind(sum_of_args_2, _1, 2)(i)==3);
|
||||
BOOST_TEST(bind(sum_of_args_3, _1, 2, 3)(i)==6);
|
||||
BOOST_TEST(bind(sum_of_args_4, _1, 2, 3, 4)(i)==10);
|
||||
BOOST_TEST(bind(sum_of_args_5, _1, 2, 3, 4, 5)(i)==15);
|
||||
BOOST_TEST(bind(sum_of_args_6, _1, 2, 3, 4, 5, 6)(i)==21);
|
||||
BOOST_TEST(bind(sum_of_args_7, _1, 2, 3, 4, 5, 6, 7)(i)==28);
|
||||
BOOST_TEST(bind(sum_of_args_8, _1, 2, 3, 4, 5, 6, 7, 8)(i)==36);
|
||||
BOOST_TEST(bind(sum_of_args_9, _1, 2, 3, 4, 5, 6, 7, 8, 9)(i)==45);
|
||||
BOOST_CHECK(bind(sum_of_args_0)()==0);
|
||||
BOOST_CHECK(bind(sum_of_args_1, _1)(i)==1);
|
||||
BOOST_CHECK(bind(sum_of_args_2, _1, 2)(i)==3);
|
||||
BOOST_CHECK(bind(sum_of_args_3, _1, 2, 3)(i)==6);
|
||||
BOOST_CHECK(bind(sum_of_args_4, _1, 2, 3, 4)(i)==10);
|
||||
BOOST_CHECK(bind(sum_of_args_5, _1, 2, 3, 4, 5)(i)==15);
|
||||
BOOST_CHECK(bind(sum_of_args_6, _1, 2, 3, 4, 5, 6)(i)==21);
|
||||
BOOST_CHECK(bind(sum_of_args_7, _1, 2, 3, 4, 5, 6, 7)(i)==28);
|
||||
BOOST_CHECK(bind(sum_of_args_8, _1, 2, 3, 4, 5, 6, 7, 8)(i)==36);
|
||||
BOOST_CHECK(bind(sum_of_args_9, _1, 2, 3, 4, 5, 6, 7, 8, 9)(i)==45);
|
||||
|
||||
// two open arguments
|
||||
BOOST_TEST(bind(sum_of_args_0)()==0);
|
||||
BOOST_TEST(bind(sum_of_args_1, _1)(i)==1);
|
||||
BOOST_TEST(bind(sum_of_args_2, _1, _2)(i, j)==3);
|
||||
BOOST_TEST(bind(sum_of_args_3, _1, _2, 3)(i, j)==6);
|
||||
BOOST_TEST(bind(sum_of_args_4, _1, _2, 3, 4)(i, j)==10);
|
||||
BOOST_TEST(bind(sum_of_args_5, _1, _2, 3, 4, 5)(i, j)==15);
|
||||
BOOST_TEST(bind(sum_of_args_6, _1, _2, 3, 4, 5, 6)(i, j)==21);
|
||||
BOOST_TEST(bind(sum_of_args_7, _1, _2, 3, 4, 5, 6, 7)(i, j)==28);
|
||||
BOOST_TEST(bind(sum_of_args_8, _1, _2, 3, 4, 5, 6, 7, 8)(i, j)==36);
|
||||
BOOST_TEST(bind(sum_of_args_9, _1, _2, 3, 4, 5, 6, 7, 8, 9)(i, j)==45);
|
||||
BOOST_CHECK(bind(sum_of_args_0)()==0);
|
||||
BOOST_CHECK(bind(sum_of_args_1, _1)(i)==1);
|
||||
BOOST_CHECK(bind(sum_of_args_2, _1, _2)(i, j)==3);
|
||||
BOOST_CHECK(bind(sum_of_args_3, _1, _2, 3)(i, j)==6);
|
||||
BOOST_CHECK(bind(sum_of_args_4, _1, _2, 3, 4)(i, j)==10);
|
||||
BOOST_CHECK(bind(sum_of_args_5, _1, _2, 3, 4, 5)(i, j)==15);
|
||||
BOOST_CHECK(bind(sum_of_args_6, _1, _2, 3, 4, 5, 6)(i, j)==21);
|
||||
BOOST_CHECK(bind(sum_of_args_7, _1, _2, 3, 4, 5, 6, 7)(i, j)==28);
|
||||
BOOST_CHECK(bind(sum_of_args_8, _1, _2, 3, 4, 5, 6, 7, 8)(i, j)==36);
|
||||
BOOST_CHECK(bind(sum_of_args_9, _1, _2, 3, 4, 5, 6, 7, 8, 9)(i, j)==45);
|
||||
|
||||
// three open arguments
|
||||
BOOST_TEST(bind(sum_of_args_0)()==0);
|
||||
BOOST_TEST(bind(sum_of_args_1, _1)(i)==1);
|
||||
BOOST_TEST(bind(sum_of_args_2, _1, _2)(i, j)==3);
|
||||
BOOST_TEST(bind(sum_of_args_3, _1, _2, _3)(i, j, k)==6);
|
||||
BOOST_TEST(bind(sum_of_args_4, _1, _2, _3, 4)(i, j, k)==10);
|
||||
BOOST_TEST(bind(sum_of_args_5, _1, _2, _3, 4, 5)(i, j, k)==15);
|
||||
BOOST_TEST(bind(sum_of_args_6, _1, _2, _3, 4, 5, 6)(i, j, k)==21);
|
||||
BOOST_TEST(bind(sum_of_args_7, _1, _2, _3, 4, 5, 6, 7)(i, j, k)==28);
|
||||
BOOST_TEST(bind(sum_of_args_8, _1, _2, _3, 4, 5, 6, 7, 8)(i, j, k)==36);
|
||||
BOOST_TEST(bind(sum_of_args_9, _1, _2, _3, 4, 5, 6, 7, 8, 9)(i, j, k)==45);
|
||||
BOOST_CHECK(bind(sum_of_args_0)()==0);
|
||||
BOOST_CHECK(bind(sum_of_args_1, _1)(i)==1);
|
||||
BOOST_CHECK(bind(sum_of_args_2, _1, _2)(i, j)==3);
|
||||
BOOST_CHECK(bind(sum_of_args_3, _1, _2, _3)(i, j, k)==6);
|
||||
BOOST_CHECK(bind(sum_of_args_4, _1, _2, _3, 4)(i, j, k)==10);
|
||||
BOOST_CHECK(bind(sum_of_args_5, _1, _2, _3, 4, 5)(i, j, k)==15);
|
||||
BOOST_CHECK(bind(sum_of_args_6, _1, _2, _3, 4, 5, 6)(i, j, k)==21);
|
||||
BOOST_CHECK(bind(sum_of_args_7, _1, _2, _3, 4, 5, 6, 7)(i, j, k)==28);
|
||||
BOOST_CHECK(bind(sum_of_args_8, _1, _2, _3, 4, 5, 6, 7, 8)(i, j, k)==36);
|
||||
BOOST_CHECK(bind(sum_of_args_9, _1, _2, _3, 4, 5, 6, 7, 8, 9)(i, j, k)==45);
|
||||
|
||||
// function compositions with bind
|
||||
BOOST_TEST(bind(sum_of_args_3, bind(sum_of_args_2, _1, 2), 2, 3)(i)==8);
|
||||
BOOST_TEST(
|
||||
BOOST_CHECK(bind(sum_of_args_3, bind(sum_of_args_2, _1, 2), 2, 3)(i)==8);
|
||||
BOOST_CHECK(
|
||||
bind(sum_of_args_9,
|
||||
bind(sum_of_args_0), // 0
|
||||
bind(sum_of_args_1, _1), // 1
|
||||
@@ -141,10 +140,10 @@ int test_main(int, char *[]) {
|
||||
_3,
|
||||
4)
|
||||
)(i, j, k);
|
||||
BOOST_TEST(result == 12);
|
||||
BOOST_CHECK(result == 12);
|
||||
|
||||
test_member_functions();
|
||||
|
||||
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// bll_and_function.cpp - The Boost Lambda Library -----------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -11,7 +11,8 @@
|
||||
|
||||
// test using BLL and boost::function
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
|
||||
@@ -32,12 +33,12 @@ void test_function() {
|
||||
boost::function<int (int, int)> f;
|
||||
f = _1 + _2;
|
||||
|
||||
BOOST_TEST(f(1, 2)== 3);
|
||||
BOOST_CHECK(f(1, 2)== 3);
|
||||
|
||||
int i=1; int j=2;
|
||||
boost::function<int& (int&, int)> g = _1 += _2;
|
||||
g(i, j);
|
||||
BOOST_TEST(i==3);
|
||||
BOOST_CHECK(i==3);
|
||||
|
||||
|
||||
|
||||
@@ -45,7 +46,7 @@ void test_function() {
|
||||
*sum = 0;
|
||||
boost::function<int& (int)> counter = *sum += _1;
|
||||
counter(5); // ok, sum* = 5;
|
||||
BOOST_TEST(*sum == 5);
|
||||
BOOST_CHECK(*sum == 5);
|
||||
delete sum;
|
||||
|
||||
// The next statement would lead to a dangling reference
|
||||
@@ -54,15 +55,9 @@ void test_function() {
|
||||
}
|
||||
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
test_function();
|
||||
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// cast_tests.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,7 +12,8 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
@@ -29,7 +30,7 @@ class base {
|
||||
public:
|
||||
virtual std::string class_name() const { return "const base"; }
|
||||
virtual std::string class_name() { return "base"; }
|
||||
|
||||
virtual ~base() {}
|
||||
};
|
||||
|
||||
class derived : public base {
|
||||
@@ -53,46 +54,46 @@ void do_test() {
|
||||
(var(b) = ll_static_cast<base *>(p_derived))();
|
||||
(var(d) = ll_static_cast<derived *>(b))();
|
||||
|
||||
BOOST_TEST(b->class_name() == "derived");
|
||||
BOOST_TEST(d->class_name() == "derived");
|
||||
BOOST_CHECK(b->class_name() == "derived");
|
||||
BOOST_CHECK(d->class_name() == "derived");
|
||||
|
||||
(var(b) = ll_dynamic_cast<derived *>(b))();
|
||||
BOOST_TEST(b != 0);
|
||||
BOOST_TEST(b->class_name() == "derived");
|
||||
BOOST_CHECK(b != 0);
|
||||
BOOST_CHECK(b->class_name() == "derived");
|
||||
|
||||
(var(d) = ll_dynamic_cast<derived *>(p_base))();
|
||||
BOOST_TEST(d == 0);
|
||||
BOOST_CHECK(d == 0);
|
||||
|
||||
|
||||
|
||||
const derived* p_const_derived = p_derived;
|
||||
|
||||
BOOST_TEST(p_const_derived->class_name() == "const derived");
|
||||
BOOST_CHECK(p_const_derived->class_name() == "const derived");
|
||||
(var(d) = ll_const_cast<derived *>(p_const_derived))();
|
||||
BOOST_TEST(d->class_name() == "derived");
|
||||
BOOST_CHECK(d->class_name() == "derived");
|
||||
|
||||
int i = 10;
|
||||
char* cp = reinterpret_cast<char*>(&i);
|
||||
|
||||
int* ip;
|
||||
(var(ip) = ll_reinterpret_cast<int *>(cp))();
|
||||
BOOST_TEST(*ip == 10);
|
||||
BOOST_CHECK(*ip == 10);
|
||||
|
||||
|
||||
// typeid
|
||||
|
||||
BOOST_TEST(string(ll_typeid(d)().name()) == string(typeid(d).name()));
|
||||
BOOST_CHECK(string(ll_typeid(d)().name()) == string(typeid(d).name()));
|
||||
|
||||
|
||||
// sizeof
|
||||
|
||||
BOOST_TEST(ll_sizeof(_1)(p_derived) == sizeof(p_derived));
|
||||
BOOST_TEST(ll_sizeof(_1)(*p_derived) == sizeof(*p_derived));
|
||||
BOOST_TEST(ll_sizeof(_1)(p_base) == sizeof(p_base));
|
||||
BOOST_TEST(ll_sizeof(_1)(*p_base) == sizeof(*p_base));
|
||||
BOOST_CHECK(ll_sizeof(_1)(p_derived) == sizeof(p_derived));
|
||||
BOOST_CHECK(ll_sizeof(_1)(*p_derived) == sizeof(*p_derived));
|
||||
BOOST_CHECK(ll_sizeof(_1)(p_base) == sizeof(p_base));
|
||||
BOOST_CHECK(ll_sizeof(_1)(*p_base) == sizeof(*p_base));
|
||||
|
||||
int an_array[100];
|
||||
BOOST_TEST(ll_sizeof(_1)(an_array) == 100 * sizeof(int));
|
||||
BOOST_CHECK(ll_sizeof(_1)(an_array) == 100 * sizeof(int));
|
||||
|
||||
delete p_derived;
|
||||
delete p_base;
|
||||
@@ -100,8 +101,8 @@ void do_test() {
|
||||
|
||||
}
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
do_test();
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
18
test/cmake_install_test/CMakeLists.txt
Normal file
18
test/cmake_install_test/CMakeLists.txt
Normal file
@@ -0,0 +1,18 @@
|
||||
# Copyright 2018, 2019 Peter Dimov
|
||||
# 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
|
||||
|
||||
cmake_minimum_required(VERSION 3.5...3.16)
|
||||
|
||||
project(cmake_install_test LANGUAGES CXX)
|
||||
|
||||
find_package(boost_lambda REQUIRED)
|
||||
find_package(boost_core REQUIRED)
|
||||
|
||||
add_executable(quick ../quick.cpp)
|
||||
target_link_libraries(quick Boost::lambda Boost::core)
|
||||
|
||||
enable_testing()
|
||||
add_test(quick quick)
|
||||
|
||||
add_custom_target(check COMMAND ${CMAKE_CTEST_COMMAND} --output-on-failure -C $<CONFIG>)
|
||||
21
test/cmake_subdir_test/CMakeLists.txt
Normal file
21
test/cmake_subdir_test/CMakeLists.txt
Normal file
@@ -0,0 +1,21 @@
|
||||
# Copyright 2018, 2019, 2021 Peter Dimov
|
||||
# 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
|
||||
|
||||
cmake_minimum_required(VERSION 3.5...3.16)
|
||||
|
||||
project(cmake_subdir_test LANGUAGES CXX)
|
||||
|
||||
set(BOOST_INCLUDE_LIBRARIES lambda)
|
||||
|
||||
add_subdirectory(../../../../ deps/boost)
|
||||
|
||||
# --target check
|
||||
|
||||
add_executable(quick ../quick.cpp)
|
||||
target_link_libraries(quick Boost::lambda Boost::core)
|
||||
|
||||
enable_testing()
|
||||
add_test(quick quick)
|
||||
|
||||
add_custom_target(check COMMAND ${CMAKE_CTEST_COMMAND} --output-on-failure -C $<CONFIG>)
|
||||
@@ -1,6 +1,6 @@
|
||||
// constructor_tests.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,7 +12,8 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
@@ -24,8 +25,12 @@
|
||||
#include <algorithm>
|
||||
#include <vector>
|
||||
|
||||
#ifdef BOOST_MSVC
|
||||
#pragma warning(disable:4512)
|
||||
#endif
|
||||
|
||||
using namespace boost::lambda;
|
||||
using namespace std;
|
||||
namespace bl = boost::lambda;
|
||||
|
||||
template<class T>
|
||||
bool check_tuple(int n, const T& t)
|
||||
@@ -34,7 +39,7 @@ bool check_tuple(int n, const T& t)
|
||||
}
|
||||
|
||||
template <>
|
||||
bool check_tuple(int n, const null_type& ) { return true; }
|
||||
bool check_tuple(int /*n*/, const null_type& ) { return true; }
|
||||
|
||||
|
||||
void constructor_all_lengths()
|
||||
@@ -45,63 +50,63 @@ void constructor_all_lengths()
|
||||
bind(constructor<tuple<int> >(),
|
||||
1)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
bind(constructor<tuple<int, int> >(),
|
||||
1, 2)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
bind(constructor<tuple<int, int, int> >(),
|
||||
1, 2, 3)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
bind(constructor<tuple<int, int, int, int> >(),
|
||||
1, 2, 3, 4)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
bind(constructor<tuple<int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
bind(constructor<tuple<int, int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5, 6)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
bind(constructor<tuple<int, int, int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5, 6, 7)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
bind(constructor<tuple<int, int, int, int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5, 6, 7, 8)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
bind(constructor<tuple<int, int, int, int, int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5, 6, 7, 8, 9)()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
}
|
||||
|
||||
@@ -113,63 +118,63 @@ void new_ptr_all_lengths()
|
||||
*(bind(new_ptr<tuple<int> >(),
|
||||
1))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
*(bind(new_ptr<tuple<int, int> >(),
|
||||
1, 2))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
*(bind(new_ptr<tuple<int, int, int> >(),
|
||||
1, 2, 3))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
*(bind(new_ptr<tuple<int, int, int, int> >(),
|
||||
1, 2, 3, 4))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
*(bind(new_ptr<tuple<int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
*(bind(new_ptr<tuple<int, int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5, 6))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
*(bind(new_ptr<tuple<int, int, int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5, 6, 7))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
*(bind(new_ptr<tuple<int, int, int, int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5, 6, 7, 8))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
ok = check_tuple(
|
||||
1,
|
||||
*(bind(new_ptr<tuple<int, int, int, int, int, int, int, int, int> >(),
|
||||
1, 2, 3, 4, 5, 6, 7, 8, 9))()
|
||||
);
|
||||
BOOST_TEST(ok);
|
||||
BOOST_CHECK(ok);
|
||||
|
||||
}
|
||||
|
||||
@@ -183,17 +188,17 @@ public:
|
||||
void test_destructor ()
|
||||
{
|
||||
char space[sizeof(is_destructor_called)];
|
||||
bool flag;
|
||||
bool flag = false;
|
||||
|
||||
is_destructor_called* idc = new(space) is_destructor_called(flag);
|
||||
BOOST_TEST(flag == false);
|
||||
BOOST_CHECK(flag == false);
|
||||
bind(destructor(), _1)(idc);
|
||||
BOOST_TEST(flag == true);
|
||||
BOOST_CHECK(flag == true);
|
||||
|
||||
idc = new(space) is_destructor_called(flag);
|
||||
BOOST_TEST(flag == false);
|
||||
BOOST_CHECK(flag == false);
|
||||
bind(destructor(), _1)(*idc);
|
||||
BOOST_TEST(flag == true);
|
||||
BOOST_CHECK(flag == true);
|
||||
}
|
||||
|
||||
|
||||
@@ -208,18 +213,18 @@ int count_deletes::count = 0;
|
||||
void test_news_and_deletes ()
|
||||
{
|
||||
int* i[10];
|
||||
for_each(i, i+10, _1 = bind(new_ptr<int>(), 2));
|
||||
std::for_each(i, i+10, _1 = bind(new_ptr<int>(), 2));
|
||||
int count_errors = 0;
|
||||
|
||||
for_each(i, i+10, (*_1 == 2) || ++var(count_errors));
|
||||
BOOST_TEST(count_errors == 0);
|
||||
std::for_each(i, i+10, (*_1 == 2) || ++var(count_errors));
|
||||
BOOST_CHECK(count_errors == 0);
|
||||
|
||||
|
||||
count_deletes* ct[10];
|
||||
for_each(ct, ct+10, _1 = bind(new_ptr<count_deletes>()));
|
||||
std::for_each(ct, ct+10, _1 = bind(new_ptr<count_deletes>()));
|
||||
count_deletes::count = 0;
|
||||
for_each(ct, ct+10, bind(delete_ptr(), _1));
|
||||
BOOST_TEST(count_deletes::count == 10);
|
||||
std::for_each(ct, ct+10, bind(delete_ptr(), _1));
|
||||
BOOST_CHECK(count_deletes::count == 10);
|
||||
|
||||
}
|
||||
|
||||
@@ -230,25 +235,25 @@ void test_array_new_and_delete()
|
||||
count_deletes::count = 0;
|
||||
|
||||
bind(delete_array(), _1)(c);
|
||||
BOOST_TEST(count_deletes::count == 5);
|
||||
BOOST_CHECK(count_deletes::count == 5);
|
||||
}
|
||||
|
||||
|
||||
void delayed_construction()
|
||||
{
|
||||
vector<int> x(3);
|
||||
vector<int> y(3);
|
||||
std::vector<int> x(3);
|
||||
std::vector<int> y(3);
|
||||
|
||||
fill(x.begin(), x.end(), 0);
|
||||
fill(y.begin(), y.end(), 1);
|
||||
std::fill(x.begin(), x.end(), 0);
|
||||
std::fill(y.begin(), y.end(), 1);
|
||||
|
||||
vector<pair<int, int> > v;
|
||||
std::vector<std::pair<int, int> > v;
|
||||
|
||||
transform(x.begin(), x.end(), y.begin(), back_inserter(v),
|
||||
bind(constructor<pair<int, int> >(), _1, _2) );
|
||||
std::transform(x.begin(), x.end(), y.begin(), std::back_inserter(v),
|
||||
bl::bind(constructor<std::pair<int, int> >(), _1, _2) );
|
||||
}
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
constructor_all_lengths();
|
||||
new_ptr_all_lengths();
|
||||
@@ -257,5 +262,5 @@ int test_main(int, char *[]) {
|
||||
test_news_and_deletes();
|
||||
test_array_new_and_delete();
|
||||
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// -- control_structures.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -11,7 +11,8 @@
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
#include "boost/lambda/if.hpp"
|
||||
@@ -50,41 +51,41 @@ void simple_loops() {
|
||||
int i;
|
||||
int arithmetic_series = 0;
|
||||
for_loop(_1 = 0, _1 < 10, _1++, arithmetic_series += _1)(i);
|
||||
BOOST_TEST(arithmetic_series == 45);
|
||||
BOOST_CHECK(arithmetic_series == 45);
|
||||
|
||||
// no body case
|
||||
for_loop(boost::lambda::var(i) = 0, boost::lambda::var(i) < 100, ++boost::lambda::var(i))();
|
||||
BOOST_TEST(i == 100);
|
||||
BOOST_CHECK(i == 100);
|
||||
|
||||
// while loops -------------------------------------------------------
|
||||
int a = 0, b = 0, c = 0;
|
||||
|
||||
while_loop((_1 + _2) >= (_1 * _2), (++_1, ++_2, ++_3))(a, b, c);
|
||||
BOOST_TEST(c == 3);
|
||||
BOOST_CHECK(c == 3);
|
||||
|
||||
int count;
|
||||
count = 0; i = 0;
|
||||
while_loop(_1++ < 10, ++boost::lambda::var(count))(i);
|
||||
BOOST_TEST(count == 10);
|
||||
BOOST_CHECK(count == 10);
|
||||
|
||||
// note that the first parameter of do_while_loop is the condition
|
||||
count = 0; i = 0;
|
||||
do_while_loop(_1++ < 10, ++boost::lambda::var(count))(i);
|
||||
BOOST_TEST(count == 11);
|
||||
BOOST_CHECK(count == 11);
|
||||
|
||||
a = 0;
|
||||
do_while_loop(constant(false), _1++)(a);
|
||||
BOOST_TEST(a == 1);
|
||||
BOOST_CHECK(a == 1);
|
||||
|
||||
// no body cases
|
||||
a = 40; b = 30;
|
||||
while_loop(--_1 > _2)(a, b);
|
||||
BOOST_TEST(a == b);
|
||||
BOOST_CHECK(a == b);
|
||||
|
||||
// (the no body case for do_while_loop is pretty redundant)
|
||||
a = 40; b = 30;
|
||||
do_while_loop(--_1 > _2)(a, b);
|
||||
BOOST_TEST(a == b);
|
||||
BOOST_CHECK(a == b);
|
||||
|
||||
|
||||
}
|
||||
@@ -93,31 +94,31 @@ void simple_ifs () {
|
||||
|
||||
int value = 42;
|
||||
if_then(_1 < 0, _1 = 0)(value);
|
||||
BOOST_TEST(value == 42);
|
||||
BOOST_CHECK(value == 42);
|
||||
|
||||
value = -42;
|
||||
if_then(_1 < 0, _1 = -_1)(value);
|
||||
BOOST_TEST(value == 42);
|
||||
BOOST_CHECK(value == 42);
|
||||
|
||||
int min;
|
||||
if_then_else(_1 < _2, boost::lambda::var(min) = _1, boost::lambda::var(min) = _2)
|
||||
(make_const(1), make_const(2));
|
||||
BOOST_TEST(min == 1);
|
||||
BOOST_CHECK(min == 1);
|
||||
|
||||
if_then_else(_1 < _2, boost::lambda::var(min) = _1, boost::lambda::var(min) = _2)
|
||||
(make_const(5), make_const(3));
|
||||
BOOST_TEST(min == 3);
|
||||
BOOST_CHECK(min == 3);
|
||||
|
||||
int x, y;
|
||||
x = -1; y = 1;
|
||||
BOOST_TEST(if_then_else_return(_1 < _2, _2, _1)(x, y) == (std::max)(x ,y));
|
||||
BOOST_TEST(if_then_else_return(_1 < _2, _2, _1)(y, x) == (std::max)(x ,y));
|
||||
BOOST_CHECK(if_then_else_return(_1 < _2, _2, _1)(x, y) == (std::max)(x ,y));
|
||||
BOOST_CHECK(if_then_else_return(_1 < _2, _2, _1)(y, x) == (std::max)(x ,y));
|
||||
}
|
||||
|
||||
|
||||
int test_main(int, char *[])
|
||||
int main()
|
||||
{
|
||||
simple_loops();
|
||||
simple_ifs();
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// -- exception_test.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -11,7 +11,8 @@
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
|
||||
@@ -29,7 +30,7 @@ using namespace boost::lambda;
|
||||
using namespace std;
|
||||
|
||||
// to prevent unused variables warnings
|
||||
template <class T> void dummy(const T& t) {}
|
||||
template <class T> void dummy(const T&) {}
|
||||
|
||||
void erroneous_exception_related_lambda_expressions() {
|
||||
|
||||
@@ -98,7 +99,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 1);
|
||||
BOOST_CHECK(ecount == 1);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=2; i++)
|
||||
@@ -113,7 +114,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 2);
|
||||
BOOST_CHECK(ecount == 2);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=3; i++)
|
||||
@@ -131,7 +132,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 3);
|
||||
BOOST_CHECK(ecount == 3);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=4; i++)
|
||||
@@ -152,7 +153,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 4);
|
||||
BOOST_CHECK(ecount == 4);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=5; i++)
|
||||
@@ -176,7 +177,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 5);
|
||||
BOOST_CHECK(ecount == 5);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=6; i++)
|
||||
@@ -203,7 +204,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 6);
|
||||
BOOST_CHECK(ecount == 6);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=7; i++)
|
||||
@@ -233,7 +234,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 7);
|
||||
BOOST_CHECK(ecount == 7);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=8; i++)
|
||||
@@ -266,7 +267,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 8);
|
||||
BOOST_CHECK(ecount == 8);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=9; i++)
|
||||
@@ -302,7 +303,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 9);
|
||||
BOOST_CHECK(ecount == 9);
|
||||
|
||||
|
||||
// with catch(...) blocks
|
||||
@@ -317,7 +318,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 1);
|
||||
BOOST_CHECK(ecount == 1);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=2; i++)
|
||||
@@ -332,7 +333,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 2);
|
||||
BOOST_CHECK(ecount == 2);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=3; i++)
|
||||
@@ -350,7 +351,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 3);
|
||||
BOOST_CHECK(ecount == 3);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=4; i++)
|
||||
@@ -371,7 +372,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 4);
|
||||
BOOST_CHECK(ecount == 4);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=5; i++)
|
||||
@@ -395,7 +396,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 5);
|
||||
BOOST_CHECK(ecount == 5);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=6; i++)
|
||||
@@ -422,7 +423,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 6);
|
||||
BOOST_CHECK(ecount == 6);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=7; i++)
|
||||
@@ -452,7 +453,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 7);
|
||||
BOOST_CHECK(ecount == 7);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=8; i++)
|
||||
@@ -485,7 +486,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 8);
|
||||
BOOST_CHECK(ecount == 8);
|
||||
|
||||
ecount = 0;
|
||||
for(int i=1; i<=9; i++)
|
||||
@@ -521,7 +522,7 @@ void test_different_number_of_catch_blocks() {
|
||||
)
|
||||
)(i);
|
||||
}
|
||||
BOOST_TEST(ecount == 9);
|
||||
BOOST_CHECK(ecount == 9);
|
||||
}
|
||||
|
||||
void test_empty_catch_blocks() {
|
||||
@@ -551,7 +552,7 @@ void return_type_matching() {
|
||||
|
||||
int i = 1;
|
||||
|
||||
BOOST_TEST(
|
||||
BOOST_CHECK(
|
||||
|
||||
try_catch(
|
||||
_1 + 1,
|
||||
@@ -575,14 +576,14 @@ void return_type_matching() {
|
||||
make_void(_1 += 1),
|
||||
catch_exception<char>(_e) // since try is void, catch can return anything
|
||||
)(i);
|
||||
BOOST_TEST(i == 2);
|
||||
BOOST_CHECK(i == 2);
|
||||
|
||||
try_catch(
|
||||
(_1 += 1, throw_exception('a')),
|
||||
catch_exception<char>(_e) // since try throws, it is void,
|
||||
// so catch can return anything
|
||||
)(i);
|
||||
BOOST_TEST(i == 3);
|
||||
BOOST_CHECK(i == 3);
|
||||
|
||||
char a = 'a';
|
||||
try_catch(
|
||||
@@ -592,10 +593,10 @@ void return_type_matching() {
|
||||
),
|
||||
catch_exception<char>( _1 = _e )
|
||||
)(a);
|
||||
BOOST_TEST(a == 'b');
|
||||
BOOST_CHECK(a == 'b');
|
||||
}
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
try
|
||||
{
|
||||
@@ -603,19 +604,15 @@ int test_main(int, char *[]) {
|
||||
return_type_matching();
|
||||
test_empty_catch_blocks();
|
||||
}
|
||||
catch (int x)
|
||||
catch (int)
|
||||
{
|
||||
BOOST_TEST(false);
|
||||
BOOST_CHECK(false);
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
BOOST_TEST(false);
|
||||
BOOST_CHECK(false);
|
||||
}
|
||||
|
||||
|
||||
return EXIT_SUCCESS;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// extending_return_type_traits.cpp -- The Boost Lambda Library --------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,10 +12,12 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/bind.hpp"
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
#include "boost/lambda/detail/suppress_unused.hpp"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
@@ -23,6 +25,8 @@
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
using boost::lambda::detail::suppress_unused_variable_warnings;
|
||||
|
||||
class A {};
|
||||
class B {};
|
||||
|
||||
@@ -81,7 +85,7 @@ struct plain_return_type_1<other_action<contentsof_action>, A> {
|
||||
} // lambda
|
||||
} // boost
|
||||
|
||||
void ok(B b) {}
|
||||
void ok(B /*b*/) {}
|
||||
|
||||
void test_unary_operators()
|
||||
{
|
||||
@@ -96,7 +100,7 @@ void test_unary_operators()
|
||||
ok((&_1)(a));
|
||||
ok((*_1)(a));
|
||||
|
||||
BOOST_TEST((*_1)(make_const(&i)) == 1);
|
||||
BOOST_CHECK((*_1)(make_const(&i)) == 1);
|
||||
}
|
||||
|
||||
class X {};
|
||||
@@ -127,7 +131,7 @@ class my_vector {};
|
||||
|
||||
template<class A, class B>
|
||||
my_vector<typename return_type_2<arithmetic_action<plus_action>, A&, B&>::type>
|
||||
operator+(const my_vector<A>& a, const my_vector<B>& b)
|
||||
operator+(const my_vector<A>& /*a*/, const my_vector<B>& /*b*/)
|
||||
{
|
||||
typedef typename
|
||||
return_type_2<arithmetic_action<plus_action>, A&, B&>::type res_type;
|
||||
@@ -175,8 +179,8 @@ Z operator^=( X&, const Y&) { return Z(); }
|
||||
// assignment
|
||||
class Assign {
|
||||
public:
|
||||
void operator=(const Assign& a) {}
|
||||
X operator[](const int& i) { return X(); }
|
||||
void operator=(const Assign& /*a*/) {}
|
||||
X operator[](const int& /*i*/) { return X(); }
|
||||
};
|
||||
|
||||
|
||||
@@ -329,9 +333,16 @@ void test_binary_operators() {
|
||||
XX dummy3 = (_1 * _2)(vxx, vyy);
|
||||
VV dummy4 = (_1 * _2)(cvxx, cvyy);
|
||||
|
||||
suppress_unused_variable_warnings(dummy1);
|
||||
suppress_unused_variable_warnings(dummy2);
|
||||
suppress_unused_variable_warnings(dummy3);
|
||||
suppress_unused_variable_warnings(dummy4);
|
||||
|
||||
my_vector<int> v1; my_vector<double> v2;
|
||||
my_vector<double> d = (_1 + _2)(v1, v2);
|
||||
|
||||
suppress_unused_variable_warnings(d);
|
||||
|
||||
// bitwise
|
||||
|
||||
(_1 << _2)(x, y);
|
||||
@@ -371,14 +382,8 @@ void test_binary_operators() {
|
||||
}
|
||||
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
test_unary_operators();
|
||||
test_binary_operators();
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// is_instance_of_test.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,7 +12,8 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
|
||||
#include "boost/lambda/detail/is_instance_of.hpp"
|
||||
@@ -45,7 +46,7 @@ template <bool b> class X {};
|
||||
X<boost::lambda::is_instance_of_2<int, A2>::value> x;
|
||||
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
using boost::lambda::is_instance_of_1;
|
||||
using boost::lambda::is_instance_of_2;
|
||||
@@ -53,27 +54,26 @@ using boost::lambda::is_instance_of_3;
|
||||
using boost::lambda::is_instance_of_4;
|
||||
|
||||
|
||||
BOOST_TEST((is_instance_of_1<B1, A1>::value == true));
|
||||
BOOST_TEST((is_instance_of_1<A1<float>, A1>::value == true));
|
||||
BOOST_TEST((is_instance_of_1<int, A1>::value == false));
|
||||
BOOST_TEST((is_instance_of_1<C1, A1>::value == false));
|
||||
BOOST_CHECK((is_instance_of_1<B1, A1>::value == true));
|
||||
BOOST_CHECK((is_instance_of_1<A1<float>, A1>::value == true));
|
||||
BOOST_CHECK((is_instance_of_1<int, A1>::value == false));
|
||||
BOOST_CHECK((is_instance_of_1<C1, A1>::value == false));
|
||||
|
||||
BOOST_TEST((is_instance_of_2<B2, A2>::value == true));
|
||||
BOOST_TEST((is_instance_of_2<A2<int, float>, A2>::value == true));
|
||||
BOOST_TEST((is_instance_of_2<int, A2>::value == false));
|
||||
BOOST_TEST((is_instance_of_2<C2, A2>::value == false));
|
||||
BOOST_CHECK((is_instance_of_2<B2, A2>::value == true));
|
||||
BOOST_CHECK((is_instance_of_2<A2<int, float>, A2>::value == true));
|
||||
BOOST_CHECK((is_instance_of_2<int, A2>::value == false));
|
||||
BOOST_CHECK((is_instance_of_2<C2, A2>::value == false));
|
||||
|
||||
BOOST_TEST((is_instance_of_3<B3, A3>::value == true));
|
||||
BOOST_TEST((is_instance_of_3<A3<int, float, char>, A3>::value == true));
|
||||
BOOST_TEST((is_instance_of_3<int, A3>::value == false));
|
||||
BOOST_TEST((is_instance_of_3<C3, A3>::value == false));
|
||||
BOOST_CHECK((is_instance_of_3<B3, A3>::value == true));
|
||||
BOOST_CHECK((is_instance_of_3<A3<int, float, char>, A3>::value == true));
|
||||
BOOST_CHECK((is_instance_of_3<int, A3>::value == false));
|
||||
BOOST_CHECK((is_instance_of_3<C3, A3>::value == false));
|
||||
|
||||
BOOST_TEST((is_instance_of_4<B4, A4>::value == true));
|
||||
BOOST_TEST((is_instance_of_4<A4<int, float, char, double>, A4>::value == true));
|
||||
BOOST_TEST((is_instance_of_4<int, A4>::value == false));
|
||||
BOOST_TEST((is_instance_of_4<C4, A4>::value == false));
|
||||
BOOST_CHECK((is_instance_of_4<B4, A4>::value == true));
|
||||
BOOST_CHECK((is_instance_of_4<A4<int, float, char, double>, A4>::value == true));
|
||||
BOOST_CHECK((is_instance_of_4<int, A4>::value == false));
|
||||
BOOST_CHECK((is_instance_of_4<C4, A4>::value == false));
|
||||
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
|
||||
}
|
||||
|
||||
|
||||
26
test/issue24_test.cpp
Normal file
26
test/issue24_test.cpp
Normal file
@@ -0,0 +1,26 @@
|
||||
// Copyright 2021 Peter Dimov
|
||||
// Distributed under the Boost Software License, Version 1.0.
|
||||
// https://www.boost.org/LICENSE_1_0.txt
|
||||
|
||||
#include <boost/lambda/bind.hpp>
|
||||
#include <boost/config.hpp>
|
||||
#include <functional>
|
||||
|
||||
#if defined(BOOST_NO_CXX11_HDR_FUNCTIONAL)
|
||||
|
||||
#include <boost/config/pragma_message.hpp>
|
||||
BOOST_PRAGMA_MESSAGE( "Skipping test because BOOST_NO_CXX11_HDR_FUNCTIONAL is defined" )
|
||||
int main() {}
|
||||
|
||||
#else
|
||||
|
||||
void func()
|
||||
{
|
||||
}
|
||||
|
||||
int main()
|
||||
{
|
||||
std::function<void()>( boost::lambda::bind( func ) );
|
||||
}
|
||||
|
||||
#endif
|
||||
30
test/istreambuf_test.cpp
Normal file
30
test/istreambuf_test.cpp
Normal file
@@ -0,0 +1,30 @@
|
||||
// istreambuf_test - test lambda function objects with istreambuf_iterator
|
||||
//
|
||||
// Copyright (c) 2007 Peter Dimov
|
||||
//
|
||||
// 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
|
||||
|
||||
#include <boost/lambda/lambda.hpp>
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#include <iterator>
|
||||
#include <sstream>
|
||||
#include <algorithm>
|
||||
|
||||
int main()
|
||||
{
|
||||
using namespace boost::lambda;
|
||||
|
||||
std::stringstream is( "ax2" );
|
||||
|
||||
std::istreambuf_iterator<char> b2( is );
|
||||
std::istreambuf_iterator<char> e2;
|
||||
|
||||
std::istreambuf_iterator<char> i = std::find_if( b2, e2, _1 == 'x' );
|
||||
|
||||
BOOST_TEST( *i == 'x' );
|
||||
BOOST_TEST( std::distance( i, e2 ) == 2 );
|
||||
|
||||
return boost::report_errors();
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
// member_pointer_test.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,7 +12,8 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
@@ -50,65 +51,65 @@ void pointer_to_data_member_tests() {
|
||||
// int i = 0;
|
||||
my_struct *y = &x;
|
||||
|
||||
BOOST_TEST((_1 ->* &my_struct::mem)(y) == 3);
|
||||
BOOST_CHECK((_1 ->* &my_struct::mem)(y) == 3);
|
||||
|
||||
(_1 ->* &my_struct::mem)(y) = 4;
|
||||
BOOST_TEST(x.mem == 4);
|
||||
BOOST_CHECK(x.mem == 4);
|
||||
|
||||
((_1 ->* &my_struct::mem) = 5)(y);
|
||||
BOOST_TEST(x.mem == 5);
|
||||
BOOST_CHECK(x.mem == 5);
|
||||
|
||||
// &my_struct::mem is a temporary, must be constified
|
||||
((y ->* _1) = 6)(make_const(&my_struct::mem));
|
||||
BOOST_TEST(x.mem == 6);
|
||||
BOOST_CHECK(x.mem == 6);
|
||||
|
||||
((_1 ->* _2) = 7)(y, make_const(&my_struct::mem));
|
||||
BOOST_TEST(x.mem == 7);
|
||||
BOOST_CHECK(x.mem == 7);
|
||||
|
||||
}
|
||||
|
||||
void pointer_to_member_function_tests() {
|
||||
|
||||
my_struct *y = new my_struct(1);
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo)(y)() == (y->mem));
|
||||
BOOST_TEST( (_1 ->* &my_struct::fooc)(y)() == (y->mem));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo))() == (y->mem));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::fooc))() == (y->mem));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo))() == (y->mem));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::fooc))() == (y->mem));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo)(y)() == (y->mem));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::fooc)(y)() == (y->mem));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo))() == (y->mem));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::fooc))() == (y->mem));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo))() == (y->mem));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::fooc))() == (y->mem));
|
||||
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo1)(y)(1) == (y->mem+1));
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo1c)(y)(1) == (y->mem+1));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo1))(1) == (y->mem+1));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo1c))(1) == (y->mem+1));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo1))(1) == (y->mem+1));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo1c))(1) == (y->mem+1));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo1)(y)(1) == (y->mem+1));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo1c)(y)(1) == (y->mem+1));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo1))(1) == (y->mem+1));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo1c))(1) == (y->mem+1));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo1))(1) == (y->mem+1));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo1c))(1) == (y->mem+1));
|
||||
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo2)(y)(1,2) == (y->mem+1+2));
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo2c)(y)(1,2) == (y->mem+1+2));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo2))(1,2) == (y->mem+1+2));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo2c))(1,2) == (y->mem+1+2));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo2))(1,2) == (y->mem+1+2));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo2c))(1,2) == (y->mem+1+2));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo2)(y)(1,2) == (y->mem+1+2));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo2c)(y)(1,2) == (y->mem+1+2));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo2))(1,2) == (y->mem+1+2));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo2c))(1,2) == (y->mem+1+2));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo2))(1,2) == (y->mem+1+2));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo2c))(1,2) == (y->mem+1+2));
|
||||
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo3)(y)(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo3c)(y)(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo3))(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo3c))(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo3))(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo3c))(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo3)(y)(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo3c)(y)(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo3))(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo3c))(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo3))(1,2,3) == (y->mem+1+2+3));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo3c))(1,2,3) == (y->mem+1+2+3));
|
||||
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo4)(y)(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_TEST( (_1 ->* &my_struct::foo4c)(y)(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo4))(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_TEST( (y ->* _1)(make_const(&my_struct::foo4c))(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo4))(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_TEST( (_1 ->* _2)(y, make_const(&my_struct::foo4c))(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo4)(y)(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_CHECK( (_1 ->* &my_struct::foo4c)(y)(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo4))(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_CHECK( (y ->* _1)(make_const(&my_struct::foo4c))(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo4))(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
BOOST_CHECK( (_1 ->* _2)(y, make_const(&my_struct::foo4c))(1,2,3,4) == (y->mem+1+2+3+4));
|
||||
|
||||
|
||||
|
||||
// member functions with default values do not work (inherent language issue)
|
||||
// BOOST_TEST( (_1 ->* &my_struct::foo3default)(y)() == (y->mem+1+2+3));
|
||||
// BOOST_CHECK( (_1 ->* &my_struct::foo3default)(y)() == (y->mem+1+2+3));
|
||||
|
||||
}
|
||||
|
||||
@@ -118,11 +119,11 @@ class C {};
|
||||
class D {};
|
||||
|
||||
// ->* can be overloaded to do anything
|
||||
bool operator->*(A a, B b) {
|
||||
bool operator->*(A /*a*/, B /*b*/) {
|
||||
return false;
|
||||
}
|
||||
|
||||
bool operator->*(B b, A a) {
|
||||
bool operator->*(B /*b*/, A /*a*/) {
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -163,30 +164,29 @@ void test_overloaded_pointer_to_member()
|
||||
A a; B b;
|
||||
|
||||
// this won't work, can't deduce the return type
|
||||
// BOOST_TEST((_1->*_2)(a, b) == false);
|
||||
// BOOST_CHECK((_1->*_2)(a, b) == false);
|
||||
|
||||
// ret<bool> gives the return type
|
||||
BOOST_TEST(ret<bool>(_1->*_2)(a, b) == false);
|
||||
BOOST_TEST(ret<bool>(a->*_1)(b) == false);
|
||||
BOOST_TEST(ret<bool>(_1->*b)(a) == false);
|
||||
BOOST_TEST((ret<bool>((var(a))->*b))() == false);
|
||||
BOOST_TEST((ret<bool>((var(a))->*var(b)))() == false);
|
||||
BOOST_CHECK(ret<bool>(_1->*_2)(a, b) == false);
|
||||
BOOST_CHECK(ret<bool>(a->*_1)(b) == false);
|
||||
BOOST_CHECK(ret<bool>(_1->*b)(a) == false);
|
||||
BOOST_CHECK((ret<bool>((var(a))->*b))() == false);
|
||||
BOOST_CHECK((ret<bool>((var(a))->*var(b)))() == false);
|
||||
|
||||
|
||||
// this is ok without ret<bool> due to the return_type_2 spcialization above
|
||||
BOOST_TEST((_1->*_2)(b, a) == true);
|
||||
BOOST_TEST((b->*_1)(a) == true);
|
||||
BOOST_TEST((_1->*a)(b) == true);
|
||||
BOOST_TEST((var(b)->*a)() == true);
|
||||
BOOST_CHECK((_1->*_2)(b, a) == true);
|
||||
BOOST_CHECK((b->*_1)(a) == true);
|
||||
BOOST_CHECK((_1->*a)(b) == true);
|
||||
BOOST_CHECK((var(b)->*a)() == true);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
pointer_to_data_member_tests();
|
||||
pointer_to_member_function_tests();
|
||||
test_overloaded_pointer_to_member();
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// operator_tests_simple.cpp -- The Boost Lambda Library ---------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -13,10 +13,15 @@
|
||||
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
|
||||
#include "boost/lambda/detail/suppress_unused.hpp"
|
||||
|
||||
#include <boost/shared_ptr.hpp>
|
||||
|
||||
#include <vector>
|
||||
#include <map>
|
||||
#include <set>
|
||||
@@ -47,7 +52,7 @@ void cout_tests()
|
||||
|
||||
(os << constant("FOO"))();
|
||||
|
||||
BOOST_TEST(os.str() == std::string("10FOO"));
|
||||
BOOST_CHECK(os.str() == std::string("10FOO"));
|
||||
|
||||
|
||||
istringstream is("ABC 1");
|
||||
@@ -57,21 +62,21 @@ void cout_tests()
|
||||
is >> s;
|
||||
is >> k;
|
||||
|
||||
BOOST_TEST(s == std::string("ABC"));
|
||||
BOOST_TEST(k == 1);
|
||||
BOOST_CHECK(s == std::string("ABC"));
|
||||
BOOST_CHECK(k == 1);
|
||||
// test for constant, constant_ref and var
|
||||
i = 5;
|
||||
constant_type<int>::type ci(constant(i));
|
||||
var_type<int>::type vi(var(i));
|
||||
|
||||
(vi = _1)(make_const(100));
|
||||
BOOST_TEST((ci)() == 5);
|
||||
BOOST_TEST(i == 100);
|
||||
BOOST_CHECK((ci)() == 5);
|
||||
BOOST_CHECK(i == 100);
|
||||
|
||||
int a;
|
||||
constant_ref_type<int>::type cr(constant_ref(i));
|
||||
(++vi, var(a) = cr)();
|
||||
BOOST_TEST(i == 101);
|
||||
BOOST_CHECK(i == 101);
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -81,115 +86,117 @@ void arithmetic_operators() {
|
||||
using namespace std;
|
||||
using namespace boost::lambda;
|
||||
|
||||
BOOST_TEST((_1 + 1)(i)==2);
|
||||
BOOST_TEST(((_1 + 1) * _2)(i, j)==4);
|
||||
BOOST_TEST((_1 - 1)(i)==0);
|
||||
BOOST_CHECK((_1 + 1)(i)==2);
|
||||
BOOST_CHECK(((_1 + 1) * _2)(i, j)==4);
|
||||
BOOST_CHECK((_1 - 1)(i)==0);
|
||||
|
||||
BOOST_TEST((_1 * 2)(j)==4);
|
||||
BOOST_TEST((_1 / 2)(j)==1);
|
||||
BOOST_CHECK((_1 * 2)(j)==4);
|
||||
BOOST_CHECK((_1 / 2)(j)==1);
|
||||
|
||||
BOOST_TEST((_1 % 2)(k)==1);
|
||||
BOOST_CHECK((_1 % 2)(k)==1);
|
||||
|
||||
BOOST_TEST((-_1)(i) == -1);
|
||||
BOOST_TEST((+_1)(i) == 1);
|
||||
BOOST_CHECK((-_1)(i) == -1);
|
||||
BOOST_CHECK((+_1)(i) == 1);
|
||||
|
||||
// test that unary plus really does something
|
||||
unary_plus_tester u;
|
||||
unary_plus_tester up = (+_1)(u);
|
||||
|
||||
boost::lambda::detail::suppress_unused_variable_warnings(up);
|
||||
}
|
||||
|
||||
void bitwise_operators() {
|
||||
unsigned int ui = 2;
|
||||
|
||||
BOOST_TEST((_1 << 1)(ui)==(2 << 1));
|
||||
BOOST_TEST((_1 >> 1)(ui)==(2 >> 1));
|
||||
BOOST_CHECK((_1 << 1)(ui)==(2 << 1));
|
||||
BOOST_CHECK((_1 >> 1)(ui)==(2 >> 1));
|
||||
|
||||
BOOST_TEST((_1 & 1)(ui)==(2 & 1));
|
||||
BOOST_TEST((_1 | 1)(ui)==(2 | 1));
|
||||
BOOST_TEST((_1 ^ 1)(ui)==(2 ^ 1));
|
||||
BOOST_TEST((~_1)(ui)==~2u);
|
||||
BOOST_CHECK((_1 & 1)(ui)==(2 & 1));
|
||||
BOOST_CHECK((_1 | 1)(ui)==(2 | 1));
|
||||
BOOST_CHECK((_1 ^ 1)(ui)==(2 ^ 1));
|
||||
BOOST_CHECK((~_1)(ui)==~2u);
|
||||
}
|
||||
|
||||
void comparison_operators() {
|
||||
int i = 0, j = 1;
|
||||
|
||||
BOOST_TEST((_1 < _2)(i, j) == true);
|
||||
BOOST_TEST((_1 <= _2)(i, j) == true);
|
||||
BOOST_TEST((_1 == _2)(i, j) == false);
|
||||
BOOST_TEST((_1 != _2)(i, j) == true);
|
||||
BOOST_TEST((_1 > _2)(i, j) == false);
|
||||
BOOST_TEST((_1 >= _2)(i, j) == false);
|
||||
BOOST_CHECK((_1 < _2)(i, j) == true);
|
||||
BOOST_CHECK((_1 <= _2)(i, j) == true);
|
||||
BOOST_CHECK((_1 == _2)(i, j) == false);
|
||||
BOOST_CHECK((_1 != _2)(i, j) == true);
|
||||
BOOST_CHECK((_1 > _2)(i, j) == false);
|
||||
BOOST_CHECK((_1 >= _2)(i, j) == false);
|
||||
|
||||
BOOST_TEST((!(_1 < _2))(i, j) == false);
|
||||
BOOST_TEST((!(_1 <= _2))(i, j) == false);
|
||||
BOOST_TEST((!(_1 == _2))(i, j) == true);
|
||||
BOOST_TEST((!(_1 != _2))(i, j) == false);
|
||||
BOOST_TEST((!(_1 > _2))(i, j) == true);
|
||||
BOOST_TEST((!(_1 >= _2))(i, j) == true);
|
||||
BOOST_CHECK((!(_1 < _2))(i, j) == false);
|
||||
BOOST_CHECK((!(_1 <= _2))(i, j) == false);
|
||||
BOOST_CHECK((!(_1 == _2))(i, j) == true);
|
||||
BOOST_CHECK((!(_1 != _2))(i, j) == false);
|
||||
BOOST_CHECK((!(_1 > _2))(i, j) == true);
|
||||
BOOST_CHECK((!(_1 >= _2))(i, j) == true);
|
||||
}
|
||||
|
||||
void logical_operators() {
|
||||
|
||||
bool t = true, f = false;
|
||||
BOOST_TEST((_1 && _2)(t, t) == true);
|
||||
BOOST_TEST((_1 && _2)(t, f) == false);
|
||||
BOOST_TEST((_1 && _2)(f, t) == false);
|
||||
BOOST_TEST((_1 && _2)(f, f) == false);
|
||||
BOOST_CHECK((_1 && _2)(t, t) == true);
|
||||
BOOST_CHECK((_1 && _2)(t, f) == false);
|
||||
BOOST_CHECK((_1 && _2)(f, t) == false);
|
||||
BOOST_CHECK((_1 && _2)(f, f) == false);
|
||||
|
||||
BOOST_TEST((_1 || _2)(t, t) == true);
|
||||
BOOST_TEST((_1 || _2)(t, f) == true);
|
||||
BOOST_TEST((_1 || _2)(f, t) == true);
|
||||
BOOST_TEST((_1 || _2)(f, f) == false);
|
||||
BOOST_CHECK((_1 || _2)(t, t) == true);
|
||||
BOOST_CHECK((_1 || _2)(t, f) == true);
|
||||
BOOST_CHECK((_1 || _2)(f, t) == true);
|
||||
BOOST_CHECK((_1 || _2)(f, f) == false);
|
||||
|
||||
BOOST_TEST((!_1)(t) == false);
|
||||
BOOST_TEST((!_1)(f) == true);
|
||||
BOOST_CHECK((!_1)(t) == false);
|
||||
BOOST_CHECK((!_1)(f) == true);
|
||||
|
||||
// test short circuiting
|
||||
int i=0;
|
||||
|
||||
(false && ++_1)(i);
|
||||
BOOST_TEST(i==0);
|
||||
BOOST_CHECK(i==0);
|
||||
i = 0;
|
||||
|
||||
(true && ++_1)(i);
|
||||
BOOST_TEST(i==1);
|
||||
BOOST_CHECK(i==1);
|
||||
i = 0;
|
||||
|
||||
(false || ++_1)(i);
|
||||
BOOST_TEST(i==1);
|
||||
BOOST_CHECK(i==1);
|
||||
i = 0;
|
||||
|
||||
(true || ++_1)(i);
|
||||
BOOST_TEST(i==0);
|
||||
BOOST_CHECK(i==0);
|
||||
i = 0;
|
||||
}
|
||||
|
||||
void unary_incs_and_decs() {
|
||||
int i = 0;
|
||||
|
||||
BOOST_TEST(_1++(i) == 0);
|
||||
BOOST_TEST(i == 1);
|
||||
BOOST_CHECK(_1++(i) == 0);
|
||||
BOOST_CHECK(i == 1);
|
||||
i = 0;
|
||||
|
||||
BOOST_TEST(_1--(i) == 0);
|
||||
BOOST_TEST(i == -1);
|
||||
BOOST_CHECK(_1--(i) == 0);
|
||||
BOOST_CHECK(i == -1);
|
||||
i = 0;
|
||||
|
||||
BOOST_TEST((++_1)(i) == 1);
|
||||
BOOST_TEST(i == 1);
|
||||
BOOST_CHECK((++_1)(i) == 1);
|
||||
BOOST_CHECK(i == 1);
|
||||
i = 0;
|
||||
|
||||
BOOST_TEST((--_1)(i) == -1);
|
||||
BOOST_TEST(i == -1);
|
||||
BOOST_CHECK((--_1)(i) == -1);
|
||||
BOOST_CHECK(i == -1);
|
||||
i = 0;
|
||||
|
||||
// the result of prefix -- and ++ are lvalues
|
||||
(++_1)(i) = 10;
|
||||
BOOST_TEST(i==10);
|
||||
BOOST_CHECK(i==10);
|
||||
i = 0;
|
||||
|
||||
(--_1)(i) = 10;
|
||||
BOOST_TEST(i==10);
|
||||
BOOST_CHECK(i==10);
|
||||
i = 0;
|
||||
}
|
||||
|
||||
@@ -199,77 +206,93 @@ void compound_operators() {
|
||||
|
||||
// normal variable as the left operand
|
||||
(i += _1)(make_const(1));
|
||||
BOOST_TEST(i == 2);
|
||||
BOOST_CHECK(i == 2);
|
||||
|
||||
(i -= _1)(make_const(1));
|
||||
BOOST_TEST(i == 1);
|
||||
BOOST_CHECK(i == 1);
|
||||
|
||||
(i *= _1)(make_const(10));
|
||||
BOOST_TEST(i == 10);
|
||||
BOOST_CHECK(i == 10);
|
||||
|
||||
(i /= _1)(make_const(2));
|
||||
BOOST_TEST(i == 5);
|
||||
BOOST_CHECK(i == 5);
|
||||
|
||||
(i %= _1)(make_const(2));
|
||||
BOOST_TEST(i == 1);
|
||||
BOOST_CHECK(i == 1);
|
||||
|
||||
// lambda expression as a left operand
|
||||
(_1 += 1)(i);
|
||||
BOOST_TEST(i == 2);
|
||||
BOOST_CHECK(i == 2);
|
||||
|
||||
(_1 -= 1)(i);
|
||||
BOOST_TEST(i == 1);
|
||||
BOOST_CHECK(i == 1);
|
||||
|
||||
(_1 *= 10)(i);
|
||||
BOOST_TEST(i == 10);
|
||||
BOOST_CHECK(i == 10);
|
||||
|
||||
(_1 /= 2)(i);
|
||||
BOOST_TEST(i == 5);
|
||||
BOOST_CHECK(i == 5);
|
||||
|
||||
(_1 %= 2)(i);
|
||||
BOOST_TEST(i == 1);
|
||||
BOOST_CHECK(i == 1);
|
||||
|
||||
// lambda expression as a left operand with rvalue on RHS
|
||||
(_1 += (0 + 1))(i);
|
||||
BOOST_CHECK(i == 2);
|
||||
|
||||
(_1 -= (0 + 1))(i);
|
||||
BOOST_CHECK(i == 1);
|
||||
|
||||
(_1 *= (0 + 10))(i);
|
||||
BOOST_CHECK(i == 10);
|
||||
|
||||
(_1 /= (0 + 2))(i);
|
||||
BOOST_CHECK(i == 5);
|
||||
|
||||
(_1 %= (0 + 2))(i);
|
||||
BOOST_CHECK(i == 1);
|
||||
|
||||
// shifts
|
||||
unsigned int ui = 2;
|
||||
(_1 <<= 1)(ui);
|
||||
BOOST_TEST(ui==(2 << 1));
|
||||
BOOST_CHECK(ui==(2 << 1));
|
||||
|
||||
ui = 2;
|
||||
(_1 >>= 1)(ui);
|
||||
BOOST_TEST(ui==(2 >> 1));
|
||||
BOOST_CHECK(ui==(2 >> 1));
|
||||
|
||||
ui = 2;
|
||||
(ui <<= _1)(make_const(1));
|
||||
BOOST_TEST(ui==(2 << 1));
|
||||
BOOST_CHECK(ui==(2 << 1));
|
||||
|
||||
ui = 2;
|
||||
(ui >>= _1)(make_const(1));
|
||||
BOOST_TEST(ui==(2 >> 1));
|
||||
BOOST_CHECK(ui==(2 >> 1));
|
||||
|
||||
// and, or, xor
|
||||
ui = 2;
|
||||
(_1 &= 1)(ui);
|
||||
BOOST_TEST(ui==(2 & 1));
|
||||
BOOST_CHECK(ui==(2 & 1));
|
||||
|
||||
ui = 2;
|
||||
(_1 |= 1)(ui);
|
||||
BOOST_TEST(ui==(2 | 1));
|
||||
BOOST_CHECK(ui==(2 | 1));
|
||||
|
||||
ui = 2;
|
||||
(_1 ^= 1)(ui);
|
||||
BOOST_TEST(ui==(2 ^ 1));
|
||||
BOOST_CHECK(ui==(2 ^ 1));
|
||||
|
||||
ui = 2;
|
||||
(ui &= _1)(make_const(1));
|
||||
BOOST_TEST(ui==(2 & 1));
|
||||
BOOST_CHECK(ui==(2 & 1));
|
||||
|
||||
ui = 2;
|
||||
(ui |= _1)(make_const(1));
|
||||
BOOST_TEST(ui==(2 | 1));
|
||||
BOOST_CHECK(ui==(2 | 1));
|
||||
|
||||
ui = 2;
|
||||
(ui ^= _1)(make_const(1));
|
||||
BOOST_TEST(ui==(2 ^ 1));
|
||||
BOOST_CHECK(ui==(2 ^ 1));
|
||||
|
||||
}
|
||||
|
||||
@@ -283,24 +306,24 @@ void assignment_and_subscript() {
|
||||
string s;
|
||||
|
||||
(_1 = "one")(s);
|
||||
BOOST_TEST(s == string("one"));
|
||||
BOOST_CHECK(s == string("one"));
|
||||
|
||||
(var(s) = "two")();
|
||||
BOOST_TEST(s == string("two"));
|
||||
BOOST_CHECK(s == string("two"));
|
||||
|
||||
BOOST_TEST((var(s)[_1])(make_const(2)) == 'o');
|
||||
BOOST_TEST((_1[2])(s) == 'o');
|
||||
BOOST_TEST((_1[_2])(s, make_const(2)) == 'o');
|
||||
BOOST_CHECK((var(s)[_1])(make_const(2)) == 'o');
|
||||
BOOST_CHECK((_1[2])(s) == 'o');
|
||||
BOOST_CHECK((_1[_2])(s, make_const(2)) == 'o');
|
||||
|
||||
// subscript returns lvalue
|
||||
(var(s)[_1])(make_const(1)) = 'o';
|
||||
BOOST_TEST(s == "too");
|
||||
BOOST_CHECK(s == "too");
|
||||
|
||||
(_1[1])(s) = 'a';
|
||||
BOOST_TEST(s == "tao");
|
||||
BOOST_CHECK(s == "tao");
|
||||
|
||||
(_1[_2])(s, make_const(0)) = 'm';
|
||||
BOOST_TEST(s == "mao");
|
||||
BOOST_CHECK(s == "mao");
|
||||
|
||||
// TODO: tests for vector, set, map, multimap
|
||||
}
|
||||
@@ -311,16 +334,26 @@ void address_of_and_dereference() {
|
||||
|
||||
A a; int i = 42;
|
||||
|
||||
BOOST_TEST((&_1)(a) == &a);
|
||||
BOOST_TEST((*&_1)(i) == 42);
|
||||
BOOST_CHECK((&_1)(a) == &a);
|
||||
BOOST_CHECK((*&_1)(i) == 42);
|
||||
|
||||
std::vector<int> vi; vi.push_back(1);
|
||||
std::vector<int>::iterator it = vi.begin();
|
||||
|
||||
(*_1 = 7)(it);
|
||||
BOOST_TEST(vi[0] == 7);
|
||||
BOOST_CHECK(vi[0] == 7);
|
||||
const std::vector<int>::iterator cit(it);
|
||||
(*_1 = 8)(cit);
|
||||
BOOST_CHECK(vi[0] == 8);
|
||||
|
||||
// TODO: Add tests for more complex iterator types
|
||||
|
||||
boost::shared_ptr<int> ptr(new int(0));
|
||||
(*_1 = 7)(ptr);
|
||||
BOOST_CHECK(*ptr == 7);
|
||||
const boost::shared_ptr<int> cptr(ptr);
|
||||
(*_1 = 8)(cptr);
|
||||
BOOST_CHECK(*ptr == 8);
|
||||
}
|
||||
|
||||
|
||||
@@ -328,7 +361,7 @@ void address_of_and_dereference() {
|
||||
void comma() {
|
||||
|
||||
int i = 100;
|
||||
BOOST_TEST((_1 = 10, 2 * _1)(i) == 20);
|
||||
BOOST_CHECK((_1 = 10, 2 * _1)(i) == 20);
|
||||
|
||||
// TODO: that the return type is the exact type of the right argument
|
||||
// (that r/l valueness is preserved)
|
||||
@@ -347,36 +380,36 @@ void pointer_arithmetic() {
|
||||
|
||||
|
||||
// non-const array
|
||||
BOOST_TEST((*(_1 + 1))(ia) == 2);
|
||||
BOOST_CHECK((*(_1 + 1))(ia) == 2);
|
||||
|
||||
// non-const pointer
|
||||
BOOST_TEST((*(_1 + 1))(ip) == 2);
|
||||
BOOST_CHECK((*(_1 + 1))(ip) == 2);
|
||||
|
||||
BOOST_TEST((*(_1 - 1))(ia_last) == 3);
|
||||
BOOST_CHECK((*(_1 - 1))(ia_last) == 3);
|
||||
|
||||
// const array
|
||||
BOOST_TEST((*(_1 + 1))(cia) == 2);
|
||||
BOOST_CHECK((*(_1 + 1))(cia) == 2);
|
||||
// const pointer
|
||||
BOOST_TEST((*(_1 + 1))(cip) == 2);
|
||||
BOOST_TEST((*(_1 - 1))(cia_last) == 3);
|
||||
BOOST_CHECK((*(_1 + 1))(cip) == 2);
|
||||
BOOST_CHECK((*(_1 - 1))(cia_last) == 3);
|
||||
|
||||
// pointer arithmetic should not make non-consts const
|
||||
(*(_1 + 2))(ia) = 0;
|
||||
(*(_1 + 3))(ip) = 0;
|
||||
|
||||
BOOST_TEST(ia[2] == 0);
|
||||
BOOST_TEST(ia[3] == 0);
|
||||
BOOST_CHECK(ia[2] == 0);
|
||||
BOOST_CHECK(ia[3] == 0);
|
||||
|
||||
// pointer - pointer
|
||||
BOOST_TEST((_1 - _2)(ia_last, ia) == 3);
|
||||
BOOST_TEST((_1 - _2)(cia_last, cia) == 3);
|
||||
BOOST_TEST((ia_last - _1)(ia) == 3);
|
||||
BOOST_TEST((cia_last - _1)(cia) == 3);
|
||||
BOOST_TEST((cia_last - _1)(cip) == 3);
|
||||
BOOST_CHECK((_1 - _2)(ia_last, ia) == 3);
|
||||
BOOST_CHECK((_1 - _2)(cia_last, cia) == 3);
|
||||
BOOST_CHECK((ia_last - _1)(ia) == 3);
|
||||
BOOST_CHECK((cia_last - _1)(cia) == 3);
|
||||
BOOST_CHECK((cia_last - _1)(cip) == 3);
|
||||
|
||||
}
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
arithmetic_operators();
|
||||
bitwise_operators();
|
||||
@@ -389,11 +422,5 @@ int test_main(int, char *[]) {
|
||||
comma();
|
||||
pointer_arithmetic();
|
||||
cout_tests();
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
// phoenix_style_control_structures.cpp -- The Boost Lambda Library ------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,7 +12,8 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
#include "boost/lambda/if.hpp"
|
||||
@@ -36,7 +37,7 @@ using namespace std;
|
||||
// If-else, while, do-while, for statements
|
||||
|
||||
|
||||
int test_main(int, char *[]) {
|
||||
int main() {
|
||||
|
||||
vector<int> v;
|
||||
v.clear();
|
||||
@@ -60,7 +61,7 @@ int test_main(int, char *[]) {
|
||||
]
|
||||
);
|
||||
|
||||
BOOST_TEST(sum == 4+5+6+7+8);
|
||||
BOOST_CHECK(sum == 4+5+6+7+8);
|
||||
|
||||
int gt = 0, eq = 0, lt = 0;
|
||||
//////////////////////////////////
|
||||
@@ -82,9 +83,9 @@ int test_main(int, char *[]) {
|
||||
]
|
||||
);
|
||||
|
||||
BOOST_TEST(lt==4);
|
||||
BOOST_TEST(eq==1);
|
||||
BOOST_TEST(gt==5);
|
||||
BOOST_CHECK(lt==4);
|
||||
BOOST_CHECK(eq==1);
|
||||
BOOST_CHECK(gt==5);
|
||||
|
||||
vector<int> t = v;
|
||||
|
||||
@@ -101,8 +102,8 @@ int test_main(int, char *[]) {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(counta == 55);
|
||||
BOOST_TEST(countb == 10);
|
||||
BOOST_CHECK(counta == 55);
|
||||
BOOST_CHECK(countb == 10);
|
||||
|
||||
|
||||
v = t;
|
||||
@@ -120,8 +121,8 @@ int test_main(int, char *[]) {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(counta == (2+11)*10/2);
|
||||
BOOST_TEST(countb == 10);
|
||||
BOOST_CHECK(counta == (2+11)*10/2);
|
||||
BOOST_CHECK(countb == 10);
|
||||
|
||||
|
||||
v = t;
|
||||
@@ -138,11 +139,10 @@ int test_main(int, char *[]) {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(counta == (1+10)*10/2);
|
||||
BOOST_TEST(countb == 10);
|
||||
BOOST_CHECK(counta == (1+10)*10/2);
|
||||
BOOST_CHECK(countb == 10);
|
||||
|
||||
v = t;
|
||||
|
||||
return 0;
|
||||
return boost::report_errors();
|
||||
}
|
||||
|
||||
|
||||
15
test/quick.cpp
Normal file
15
test/quick.cpp
Normal file
@@ -0,0 +1,15 @@
|
||||
// Copyright 2021 Peter Dimov
|
||||
// Distributed under the Boost Software License, Version 1.0.
|
||||
// https://www.boost.org/LICENSE_1_0.txt
|
||||
|
||||
#include <boost/lambda/lambda.hpp>
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
|
||||
int main()
|
||||
{
|
||||
using namespace boost::lambda;
|
||||
|
||||
BOOST_TEST_EQ( (_1 + _2)(1, 2), 3 );
|
||||
|
||||
return boost::report_errors();
|
||||
}
|
||||
317
test/result_of_tests.cpp
Normal file
317
test/result_of_tests.cpp
Normal file
@@ -0,0 +1,317 @@
|
||||
// result_of_tests.cpp -- The Boost Lambda Library ------------------
|
||||
//
|
||||
// Copyright (C) 2010 Steven Watanabe
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include <boost/lambda/bind.hpp>
|
||||
#include <boost/lambda/lambda.hpp>
|
||||
#include <boost/mpl/assert.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
|
||||
struct with_result_type {
|
||||
typedef int result_type;
|
||||
int operator()() const { return 0; }
|
||||
int operator()(int) const { return 1; }
|
||||
int operator()(int, int) const { return 2; }
|
||||
int operator()(int, int, int) const { return 3; }
|
||||
int operator()(int, int, int, int) const { return 4; }
|
||||
int operator()(int, int, int, int, int) const { return 5; }
|
||||
int operator()(int, int, int, int, int, int) const { return 6; }
|
||||
int operator()(int, int, int, int, int, int, int) const { return 7; }
|
||||
int operator()(int, int, int, int, int, int, int, int) const { return 8; }
|
||||
int operator()(int, int, int, int, int, int, int, int, int) const { return 9; }
|
||||
};
|
||||
|
||||
struct with_result_template_value {
|
||||
template<class Sig>
|
||||
struct result;
|
||||
template<class This>
|
||||
struct result<This()> {
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1>
|
||||
struct result<This(A1)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2>
|
||||
struct result<This(A1, A2)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3>
|
||||
struct result<This(A1, A2, A3)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4>
|
||||
struct result<This(A1, A2, A3, A4)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5>
|
||||
struct result<This(A1, A2, A3, A4, A5)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
struct result<This(A1, A2, A3, A4, A5, A6)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A6, int>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
struct result<This(A1, A2, A3, A4, A5, A6, A7)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A6, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A7, int>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
struct result<This(A1, A2, A3, A4, A5, A6, A7, A8)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A6, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A7, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A8, int>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9>
|
||||
struct result<This(A1, A2, A3, A4, A5, A6, A7, A8, A9)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A6, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A7, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A8, int>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A9, int>));
|
||||
typedef int type;
|
||||
};
|
||||
|
||||
int operator()() const { return 0; }
|
||||
int operator()(int) const { return 1; }
|
||||
int operator()(int, int) const { return 2; }
|
||||
int operator()(int, int, int) const { return 3; }
|
||||
int operator()(int, int, int, int) const { return 4; }
|
||||
int operator()(int, int, int, int, int) const { return 5; }
|
||||
int operator()(int, int, int, int, int, int) const { return 6; }
|
||||
int operator()(int, int, int, int, int, int, int) const { return 7; }
|
||||
int operator()(int, int, int, int, int, int, int, int) const { return 8; }
|
||||
int operator()(int, int, int, int, int, int, int, int, int) const { return 9; }
|
||||
};
|
||||
|
||||
struct with_result_template_reference {
|
||||
template<class Sig>
|
||||
struct result;
|
||||
template<class This>
|
||||
struct result<This()> {
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1>
|
||||
struct result<This(A1)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2>
|
||||
struct result<This(A1, A2)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3>
|
||||
struct result<This(A1, A2, A3)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4>
|
||||
struct result<This(A1, A2, A3, A4)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5>
|
||||
struct result<This(A1, A2, A3, A4, A5)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5, class A6>
|
||||
struct result<This(A1, A2, A3, A4, A5, A6)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A6, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5, class A6, class A7>
|
||||
struct result<This(A1, A2, A3, A4, A5, A6, A7)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A6, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A7, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8>
|
||||
struct result<This(A1, A2, A3, A4, A5, A6, A7, A8)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A6, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A7, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A8, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
template<class This, class A1, class A2, class A3, class A4, class A5, class A6, class A7, class A8, class A9>
|
||||
struct result<This(A1, A2, A3, A4, A5, A6, A7, A8, A9)> {
|
||||
BOOST_MPL_ASSERT((boost::is_same<A1, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A2, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A3, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A4, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A5, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A6, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A7, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A8, int&>));
|
||||
BOOST_MPL_ASSERT((boost::is_same<A9, int&>));
|
||||
typedef int type;
|
||||
};
|
||||
|
||||
int operator()() const { return 0; }
|
||||
int operator()(int) const { return 1; }
|
||||
int operator()(int, int) const { return 2; }
|
||||
int operator()(int, int, int) const { return 3; }
|
||||
int operator()(int, int, int, int) const { return 4; }
|
||||
int operator()(int, int, int, int, int) const { return 5; }
|
||||
int operator()(int, int, int, int, int, int) const { return 6; }
|
||||
int operator()(int, int, int, int, int, int, int) const { return 7; }
|
||||
int operator()(int, int, int, int, int, int, int, int) const { return 8; }
|
||||
int operator()(int, int, int, int, int, int, int, int, int) const { return 9; }
|
||||
};
|
||||
|
||||
template<class F>
|
||||
typename boost::result_of<F()>::type apply0(F f) {
|
||||
return f();
|
||||
}
|
||||
template<class A, class F>
|
||||
typename boost::result_of<F(A)>::type apply1(F f, A a) {
|
||||
return f(a);
|
||||
}
|
||||
template<class A, class B, class F>
|
||||
typename boost::result_of<F(A, B)>::type apply2(F f, A a, B b) {
|
||||
return f(a, b);
|
||||
}
|
||||
template<class A, class B, class C, class F>
|
||||
typename boost::result_of<F(A, B, C)>::type apply3(F f, A a, B b, C c) {
|
||||
return f(a, b, c);
|
||||
}
|
||||
|
||||
using namespace boost::lambda;
|
||||
|
||||
int main() {
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type())() == 0);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1)() == 1);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1, 2)() == 2);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1, 2, 3)() == 3);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1, 2, 3, 4)() == 4);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1, 2, 3, 4, 5)() == 5);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1, 2, 3, 4, 5, 6)() == 6);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1, 2, 3, 4, 5, 6, 7)() == 7);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1, 2, 3, 4, 5, 6, 7, 8)() == 8);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_type(), 1, 2, 3, 4, 5, 6, 7, 8, 9)() == 9);
|
||||
|
||||
// Nullary result_of fails
|
||||
//BOOST_CHECK(boost::lambda::bind(with_result_template_value())() == 0);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1)() == 1);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1, 2)() == 2);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1, 2, 3)() == 3);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1, 2, 3, 4)() == 4);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1, 2, 3, 4, 5)() == 5);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1, 2, 3, 4, 5, 6)() == 6);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1, 2, 3, 4, 5, 6, 7)() == 7);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1, 2, 3, 4, 5, 6, 7, 8)() == 8);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_value(), 1, 2, 3, 4, 5, 6, 7, 8, 9)() == 9);
|
||||
|
||||
int one = 1,
|
||||
two = 2,
|
||||
three = 3,
|
||||
four = 4,
|
||||
five = 5,
|
||||
six = 6,
|
||||
seven = 7,
|
||||
eight = 8,
|
||||
nine = 9;
|
||||
|
||||
// Nullary result_of fails
|
||||
//BOOST_CHECK(boost::lambda::bind(with_result_template_reference())() == 0);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one))() == 1);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one), var(two))() == 2);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one), var(two), var(three))() == 3);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one), var(two), var(three), var(four))() == 4);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one), var(two), var(three), var(four), var(five))() == 5);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one), var(two), var(three), var(four), var(five), var(six))() == 6);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one), var(two), var(three), var(four), var(five), var(six), var(seven))() == 7);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one), var(two), var(three), var(four), var(five), var(six), var(seven), var(eight))() == 8);
|
||||
BOOST_CHECK(boost::lambda::bind(with_result_template_reference(), var(one), var(two), var(three), var(four), var(five), var(six), var(seven), var(eight), var(nine))() == 9);
|
||||
|
||||
// Check using result_of with lambda functors
|
||||
BOOST_CHECK(apply0(constant(0)) == 0);
|
||||
// returns local address and leads to undefined behavior
|
||||
//~ BOOST_CHECK(apply1<int>(_1, one) == 1);
|
||||
BOOST_CHECK(apply1<int&>(_1, one) == 1);
|
||||
BOOST_CHECK(apply1<const int&>(_1, one) == 1);
|
||||
BOOST_CHECK((apply2<int, int>(_1 + _2, one, two) == 3));
|
||||
BOOST_CHECK((apply2<int&, int&>(_1 + _2, one, two) == 3));
|
||||
BOOST_CHECK((apply2<const int&, const int&>(_1 + _2, one, two) == 3));
|
||||
BOOST_CHECK((apply3<int, int, int>(_1 + _2 + _3, one, two, three) == 6));
|
||||
BOOST_CHECK((apply3<int&, int&, int&>(_1 + _2 + _3, one, two, three) == 6));
|
||||
BOOST_CHECK((apply3<const int&, const int&, const int&>(_1 + _2 + _3, one, two, three) == 6));
|
||||
|
||||
return boost::report_errors();
|
||||
}
|
||||
54
test/ret_test.cpp
Normal file
54
test/ret_test.cpp
Normal file
@@ -0,0 +1,54 @@
|
||||
// ret_test.cpp - The Boost Lambda Library -----------------------
|
||||
//
|
||||
// Copyright (C) 2009 Steven Watanabe
|
||||
//
|
||||
// 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)
|
||||
//
|
||||
// For more information, see www.boost.org
|
||||
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
#include <boost/lambda/lambda.hpp>
|
||||
|
||||
#include <boost/mpl/assert.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
|
||||
template<class R, class F>
|
||||
void test_ret(R r, F f) {
|
||||
typename F::result_type x = f();
|
||||
BOOST_MPL_ASSERT((boost::is_same<R, typename F::result_type>));
|
||||
BOOST_CHECK(x == r);
|
||||
}
|
||||
|
||||
template<class R, class F, class T1>
|
||||
void test_ret(R r, F f, T1& t1) {
|
||||
typename F::result_type x = f(t1);
|
||||
BOOST_MPL_ASSERT((boost::is_same<R, typename F::result_type>));
|
||||
BOOST_CHECK(x == r);
|
||||
}
|
||||
|
||||
class add_result {
|
||||
public:
|
||||
add_result(int i = 0) : value(i) {}
|
||||
friend bool operator==(const add_result& lhs, const add_result& rhs) {
|
||||
return(lhs.value == rhs.value);
|
||||
}
|
||||
private:
|
||||
int value;
|
||||
};
|
||||
|
||||
class addable {};
|
||||
add_result operator+(addable, addable) {
|
||||
return add_result(7);
|
||||
}
|
||||
|
||||
int main() {
|
||||
addable test;
|
||||
test_ret(add_result(7), boost::lambda::ret<add_result>(boost::lambda::_1 + test), test);
|
||||
test_ret(8.0, boost::lambda::ret<double>(boost::lambda::constant(7) + 1));
|
||||
|
||||
return boost::report_errors();
|
||||
}
|
||||
57
test/rvalue_test.cpp
Normal file
57
test/rvalue_test.cpp
Normal file
@@ -0,0 +1,57 @@
|
||||
// rvalue_test - test lambda function objects with rvalue arguments
|
||||
//
|
||||
// Copyright (c) 2007 Peter Dimov
|
||||
//
|
||||
// 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
|
||||
|
||||
#include <boost/lambda/lambda.hpp>
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
|
||||
int main()
|
||||
{
|
||||
using namespace boost::lambda;
|
||||
|
||||
int x = 0;
|
||||
int const y = 1;
|
||||
int const z = 2;
|
||||
|
||||
BOOST_TEST( _1( x ) == 0 );
|
||||
BOOST_TEST( _1( y ) == 1 );
|
||||
BOOST_TEST( _1( 2 ) == 2 );
|
||||
|
||||
BOOST_TEST( _2( x, x ) == 0 );
|
||||
BOOST_TEST( _2( x, y ) == 1 );
|
||||
BOOST_TEST( _2( x, 2 ) == 2 );
|
||||
|
||||
BOOST_TEST( _2( 4, x ) == 0 );
|
||||
BOOST_TEST( _2( 4, y ) == 1 );
|
||||
BOOST_TEST( _2( 4, 2 ) == 2 );
|
||||
|
||||
(_1 = _2)( x, y );
|
||||
BOOST_TEST( x == y );
|
||||
|
||||
(_1 = _2)( x, 3 );
|
||||
BOOST_TEST( x == 3 );
|
||||
|
||||
(_2 = _1)( z, x );
|
||||
BOOST_TEST( x == z );
|
||||
|
||||
(_2 = _1)( 4, x );
|
||||
BOOST_TEST( x == 4 );
|
||||
|
||||
BOOST_TEST( _3( x, x, x ) == x );
|
||||
BOOST_TEST( _3( x, x, y ) == y );
|
||||
BOOST_TEST( _3( x, x, 2 ) == 2 );
|
||||
|
||||
BOOST_TEST( _3( x, 5, x ) == x );
|
||||
BOOST_TEST( _3( x, 5, y ) == y );
|
||||
BOOST_TEST( _3( x, 5, 2 ) == 2 );
|
||||
|
||||
BOOST_TEST( _3( 9, 5, x ) == x );
|
||||
BOOST_TEST( _3( 9, 5, y ) == y );
|
||||
BOOST_TEST( _3( 9, 5, 2 ) == 2 );
|
||||
|
||||
return boost::report_errors();
|
||||
}
|
||||
@@ -1,6 +1,6 @@
|
||||
// switch_test.cpp -- The Boost Lambda Library --------------------------
|
||||
//
|
||||
// Copyright (C) 2000-2003 Jaakko Järvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Jaakko Jarvi (jaakko.jarvi@cs.utu.fi)
|
||||
// Copyright (C) 2000-2003 Gary Powell (powellg@amazon.com)
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See
|
||||
@@ -12,7 +12,8 @@
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
|
||||
#include <boost/test/minimal.hpp> // see "Header Implementation Option"
|
||||
#include <boost/core/lightweight_test.hpp>
|
||||
#define BOOST_CHECK BOOST_TEST
|
||||
|
||||
|
||||
#include "boost/lambda/lambda.hpp"
|
||||
@@ -63,7 +64,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 0));
|
||||
BOOST_CHECK(check(w, 0));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -75,7 +76,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 1));
|
||||
BOOST_CHECK(check(w, 1));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -88,7 +89,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 2));
|
||||
BOOST_CHECK(check(w, 2));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -102,7 +103,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 3));
|
||||
BOOST_CHECK(check(w, 3));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -117,7 +118,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 4));
|
||||
BOOST_CHECK(check(w, 4));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -133,7 +134,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 5));
|
||||
BOOST_CHECK(check(w, 5));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -150,7 +151,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 6));
|
||||
BOOST_CHECK(check(w, 6));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -168,7 +169,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 7));
|
||||
BOOST_CHECK(check(w, 7));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -187,7 +188,7 @@ void do_switch_no_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 8));
|
||||
BOOST_CHECK(check(w, 8));
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
}
|
||||
@@ -216,8 +217,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, -1));
|
||||
BOOST_TEST(default_count == 10);
|
||||
BOOST_CHECK(check(w, -1));
|
||||
BOOST_CHECK(default_count == 10);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -230,8 +231,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 0));
|
||||
BOOST_TEST(default_count == 9);
|
||||
BOOST_CHECK(check(w, 0));
|
||||
BOOST_CHECK(default_count == 9);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -245,8 +246,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 1));
|
||||
BOOST_TEST(default_count == 8);
|
||||
BOOST_CHECK(check(w, 1));
|
||||
BOOST_CHECK(default_count == 8);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -261,8 +262,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 2));
|
||||
BOOST_TEST(default_count == 7);
|
||||
BOOST_CHECK(check(w, 2));
|
||||
BOOST_CHECK(default_count == 7);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -278,8 +279,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 3));
|
||||
BOOST_TEST(default_count == 6);
|
||||
BOOST_CHECK(check(w, 3));
|
||||
BOOST_CHECK(default_count == 6);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -296,8 +297,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 4));
|
||||
BOOST_TEST(default_count == 5);
|
||||
BOOST_CHECK(check(w, 4));
|
||||
BOOST_CHECK(default_count == 5);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -315,8 +316,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 5));
|
||||
BOOST_TEST(default_count == 4);
|
||||
BOOST_CHECK(check(w, 5));
|
||||
BOOST_CHECK(default_count == 4);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -335,8 +336,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 6));
|
||||
BOOST_TEST(default_count == 3);
|
||||
BOOST_CHECK(check(w, 6));
|
||||
BOOST_CHECK(default_count == 3);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
// ---
|
||||
@@ -356,8 +357,8 @@ void do_switch_yes_defaults_tests() {
|
||||
)
|
||||
);
|
||||
|
||||
BOOST_TEST(check(w, 7));
|
||||
BOOST_TEST(default_count == 2);
|
||||
BOOST_CHECK(check(w, 7));
|
||||
BOOST_CHECK(default_count == 2);
|
||||
std::fill_n(w.begin(), 10, 0);
|
||||
|
||||
}
|
||||
@@ -379,14 +380,13 @@ void test_empty_cases() {
|
||||
|
||||
}
|
||||
|
||||
int test_main(int, char* []) {
|
||||
int main() {
|
||||
|
||||
do_switch_no_defaults_tests();
|
||||
do_switch_yes_defaults_tests();
|
||||
|
||||
test_empty_cases();
|
||||
|
||||
return EXIT_SUCCESS;
|
||||
return boost::report_errors();
|
||||
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user