PBeFS
Parallel Best-First Search
Loading...
Searching...
No Matches
WaterJugs.h
Go to the documentation of this file.
1/*--------------------------------------------------------------------------*/
2/*---------------------------- File WaterJugs.h ----------------------------*/
3/*--------------------------------------------------------------------------*/
17/*--------------------------------------------------------------------------*/
18/*------------------------------ DEFINITIONS -------------------------------*/
19/*--------------------------------------------------------------------------*/
20
21#ifndef __PBeFS_WaterJugs
22 #define __PBeFS_WaterJugs
23 /* self-identification: #endif at the end of the file */
24
25/*--------------------------------------------------------------------------*/
26/*-------------------------------- INCLUDES --------------------------------*/
27/*--------------------------------------------------------------------------*/
28
29#include <algorithm>
30
31#include <cstddef>
32
33#include <cstdint>
34
35#include <stdexcept>
36
37#include <utility>
38
39#include <vector>
40
41#include "PBeFS/astar/Domain.h"
42
43/*--------------------------------------------------------------------------*/
44/*------------------------------- NAMESPACE --------------------------------*/
45/*--------------------------------------------------------------------------*/
46
48namespace PBeFS_di_unipi_it
49{
50
51/*--------------------------------------------------------------------------*/
52/*---------------------------- CLASS WaterJugs -----------------------------*/
53/*--------------------------------------------------------------------------*/
55
66
67class WaterJugs {
68
69/*------------------------ PUBLIC PART OF THE CLASS ------------------------*/
70
71 public:
72
73/*------------------------------ PUBLIC TYPES ------------------------------*/
74
75 using state_type = std::uint64_t;
76 using cost_type = int;
77
78/*------------------------------ CONSTRUCTOR -------------------------------*/
79
82
83 WaterJugs( std::vector< int > capacity , int goal )
84 : v_cap( std::move( capacity ) ) , f_goal( goal ) {
85 if( v_cap.empty() || ( v_cap.size() > 4 ) )
86 throw( std::invalid_argument( "WaterJugs::WaterJugs: 1 to 4 jugs" ) );
87 for( int c : v_cap ) {
88 if( ( c <= 0 ) || ( c > 65535 ) )
89 throw( std::invalid_argument( "WaterJugs::WaterJugs: bad capacity" ) );
90 v_first.push_back( f_features );
91 f_features += std::size_t( c ) + 1;
92 }
93 }
94
95/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
97
98 [[nodiscard]] static int level( std::uint64_t s , std::size_t j ) noexcept {
99 return( int( ( s >> ( 16 * j ) ) & 0xFFFF ) );
100 }
101
103
104 [[nodiscard]] std::size_t jugs( void ) const noexcept {
105 return( v_cap.size() );
106 }
107
108/*------------------------- METHODS OF THE DOMAIN --------------------------*/
109
110 [[nodiscard]] std::uint64_t initial_state( void ) const noexcept {
111 return( 0 );
112 }
113
114 [[nodiscard]] bool is_goal( std::uint64_t s ) const noexcept {
115 for( std::size_t j = 0 ; j < v_cap.size() ; ++j )
116 if( level( s , j ) == f_goal )
117 return( true );
118 return( false );
119 }
120
121 [[nodiscard]] std::uint64_t hash( std::uint64_t s ) const noexcept {
122 return( ADS::splitmix64( s ) );
123 }
124
125 [[nodiscard]] int heuristic( std::uint64_t s ) const noexcept {
126 return( is_goal( s ) ? 0 : 1 );
127 }
128
129/*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
131
132 template< class F >
133 void for_each_successor( std::uint64_t s , int , F && f ) const {
134 const auto with = [ & ]( std::uint64_t t , std::size_t j , int l ) {
135 return( ( t & ~( std::uint64_t( 0xFFFF ) << ( 16 * j ) ) ) |
136 ( std::uint64_t( l ) << ( 16 * j ) ) );
137 };
138 const auto move = [ & ]( std::uint64_t t ) {
139 if( t != s )
140 f( t , 1 , heuristic( t ) );
141 };
142 for( std::size_t i = 0 ; i < v_cap.size() ; ++i ) {
143 move( with( s , i , v_cap[ i ] ) ); // fill i
144 move( with( s , i , 0 ) ); // empty i
145 for( std::size_t j = 0 ; j < v_cap.size() ; ++j ) // i into j
146 if( i != j ) {
147 const int q = std::min( level( s , i ) , v_cap[ j ] - level( s , j ) );
148 move( with( with( s , i , level( s , i ) - q ) , j ,
149 level( s , j ) + q ) );
150 }
151 }
152 }
153
154/*---------------------- FEATURES FOR ZOBRIST HASHING ----------------------*/
156
157 [[nodiscard]] std::size_t num_features( void ) const noexcept {
158 return( f_features );
159 }
160
162
163 template< class F >
164 void for_each_feature( std::uint64_t s , F && f ) const {
165 for( std::size_t j = 0 ; j < v_cap.size() ; ++j )
166 f( v_first[ j ] + std::size_t( level( s , j ) ) );
167 }
168
169/*------------------------------ OTHER HASHES ------------------------------*/
171
172 [[nodiscard]] std::uint64_t perfect_hash( std::uint64_t s ) const noexcept {
173 return( s );
174 }
175
176/*----------------------- PRIVATE PART OF THE CLASS ------------------------*/
177
178 private:
179
180 std::vector< int > v_cap;
181 int f_goal;
182 std::vector< std::size_t > v_first;
183 std::size_t f_features = 0;
184
185 }; // end( class( WaterJugs ) )
186
187/*--------------------------------------------------------------------------*/
188
189} // end( namespace PBeFS_di_unipi_it )
190
191/*--------------------------------------------------------------------------*/
192
193#endif /* __PBeFS_WaterJugs */
194
195/*--------------------------------------------------------------------------*/
196/*-------------------------- End File WaterJugs.h --------------------------*/
197/*--------------------------------------------------------------------------*/
Header file for the concepts a search problem has to satisfy in order to be searched by the algorithm...
static int level(std::uint64_t s, std::size_t j) noexcept
the level of the jug j in the state s
Definition WaterJugs.h:98
WaterJugs(std::vector< int > capacity, int goal)
constructor of the jugs of the given capacities, the goal being a jug holding goal units
Definition WaterJugs.h:83
bool is_goal(std::uint64_t s) const noexcept
Definition WaterJugs.h:114
std::uint64_t hash(std::uint64_t s) const noexcept
Definition WaterJugs.h:121
void for_each_feature(std::uint64_t s, F &&f) const
calls f( i ) for the feature i of the level of each jug
Definition WaterJugs.h:164
std::uint64_t state_type
the packed levels
Definition WaterJugs.h:75
int cost_type
the cost type
Definition WaterJugs.h:76
std::uint64_t perfect_hash(std::uint64_t s) const noexcept
the perfect hash: the packed state
Definition WaterJugs.h:172
std::size_t num_features(void) const noexcept
the number of features: one per jug and level
Definition WaterJugs.h:157
void for_each_successor(std::uint64_t s, int, F &&f) const
calls f( t , 1 , h( t ) ) for each fill, empty and pour that changes s
Definition WaterJugs.h:133
std::size_t jugs(void) const noexcept
the number of jugs
Definition WaterJugs.h:104
std::uint64_t initial_state(void) const noexcept
Definition WaterJugs.h:110
int heuristic(std::uint64_t s) const noexcept
Definition WaterJugs.h:125
namespace for the Parallel Best-First Search library
Definition AStar.h:83