A toolkit for working with phylogenetic data.
v0.24.0
utils/math/bitvector/operators.cpp
Go to the documentation of this file.
1 /*
2  Genesis - A toolkit for working with phylogenetic data.
3  Copyright (C) 2014-2020 Lucas Czech and HITS gGmbH
4 
5  This program is free software: you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation, either version 3 of the License, or
8  (at your option) any later version.
9 
10  This program is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  GNU General Public License for more details.
14 
15  You should have received a copy of the GNU General Public License
16  along with this program. If not, see <http://www.gnu.org/licenses/>.
17 
18  Contact:
19  Lucas Czech <lucas.czech@h-its.org>
20  Exelixis Lab, Heidelberg Institute for Theoretical Studies
21  Schloss-Wolfsbrunnenweg 35, D-69118 Heidelberg, Germany
22 */
23 
32 
33 #include <iostream>
34 #include <string>
35 
36 namespace genesis {
37 namespace utils {
38 
39 // =================================================================================================
40 // Bitvector Operators
41 // =================================================================================================
42 
43 Bitvector bitwise_and (Bitvector const& lhs, Bitvector const& rhs)
44 {
45  if( lhs.size() < rhs.size() ) {
46  auto result = Bitvector( rhs, lhs.size() );
47  result &= lhs;
48  return result;
49  } else {
50  auto result = Bitvector( lhs, rhs.size() );
51  result &= rhs;
52  return result;
53  }
54 }
55 
56 Bitvector bitwise_or (Bitvector const& lhs, Bitvector const& rhs)
57 {
58  if( lhs.size() < rhs.size() ) {
59  auto result = Bitvector( rhs, lhs.size() );
60  result |= lhs;
61  return result;
62  } else {
63  auto result = Bitvector( lhs, rhs.size() );
64  result |= rhs;
65  return result;
66  }
67 }
68 
69 Bitvector bitwise_xor (Bitvector const& lhs, Bitvector const& rhs)
70 {
71  if( lhs.size() < rhs.size() ) {
72  auto result = Bitvector( rhs, lhs.size() );
73  result ^= lhs;
74  return result;
75  } else {
76  auto result = Bitvector( lhs, rhs.size() );
77  result ^= rhs;
78  return result;
79  }
80 }
81 
82 Bitvector set_minus (Bitvector const& lhs, Bitvector const& rhs)
83 {
84  return lhs & (~rhs);
85 }
86 
88 {
89  return (lhs | rhs) & ~(lhs & rhs);
90 }
91 
92 bool is_strict_subset( Bitvector const& sub, Bitvector const& super )
93 {
94  return ((sub & super) == sub) && (sub.count() < super.count());
95 }
96 
97 bool is_strict_superset( Bitvector const& super, Bitvector const& sub )
98 {
99  return is_strict_subset( sub, super );
100 }
101 
102 bool is_subset( Bitvector const& sub, Bitvector const& super )
103 {
104  return (sub == super) || is_strict_subset(sub, super);
105 }
106 
107 bool is_superset( Bitvector const& super, Bitvector const& sub )
108 {
109  return (super == sub) || is_strict_superset(super, sub);
110 }
111 
112 std::ostream& operator << (std::ostream& s, Bitvector const& bv)
113 {
114  for( size_t i = 0; i < bv.size(); ++i ) {
115  s << (bv.get(i) ? "1" : "0");
116  }
117  return s;
118 }
119 
120 std::istream& operator >> ( std::istream& in, Bitvector& bv )
121 {
122  // We need two steps, as we have to construct the bitvector with a known size.
123  // First, bring the bits into string form...
124  std::string str;
125  auto c = in.peek();
126  while( c == '0' || c == '1' ) {
127  str += c;
128  (void) in.get();
129  c = in.peek();
130  }
131 
132  // ... then, create the bitvector.
133  bv = Bitvector( str.size() );
134  for( size_t i = 0; i < str.size(); ++i ) {
135  if( str[i] == '1' ) {
136  bv.set(i);
137  }
138  }
139  return in;
140 }
141 
142 } // namespace utils
143 } // namespace genesis
size_t count() const
Count the number of set bits in the Bitvector, that is, its Hamming weight, or population count (popc...
Definition: bitvector.cpp:223
bool is_superset(Bitvector const &super, Bitvector const &sub)
Superset or equal.
bool get(size_t index) const
Return the value of a single bit, with boundary check.
Definition: bitvector.hpp:130
std::istream & operator>>(std::istream &in, Bitvector &bv)
Extraction operator that inputs a Bitvector from a string of &#39;0&#39;s and &#39;1&#39;s, and stops at the first ch...
bool is_strict_subset(Bitvector const &sub, Bitvector const &super)
Strict subset.
void set(size_t index)
Set the value of a single bit to true, with boundary check.
Definition: bitvector.hpp:147
Bitvector symmetric_difference(Bitvector const &lhs, Bitvector const &rhs)
Container namespace for all symbols of genesis in order to keep them separate when used as a library...
std::ostream & operator<<(std::ostream &os, const Matrix< signed char > &matrix)
Template specialization for signed char, in order to print nicely.
bool is_subset(Bitvector const &sub, Bitvector const &super)
Subset or equal.
Bitvector bitwise_or(Bitvector const &lhs, Bitvector const &rhs)
Take the bitwise or of two Bitvectors of potentially different size.
Bitvector bitwise_xor(Bitvector const &lhs, Bitvector const &rhs)
Take the bitwise xor of two Bitvectors of potentially different size.
Bitvector bitwise_and(Bitvector const &lhs, Bitvector const &rhs)
Take the bitwise and of two Bitvectors of potentially different size.
bool is_strict_superset(Bitvector const &super, Bitvector const &sub)
Strict superset.
size_t size() const
Return the size (number of bits) of this Bitvector.
Definition: bitvector.hpp:230
Bitvector set_minus(Bitvector const &lhs, Bitvector const &rhs)