5 * Created by Christian Brunschen on 12/05/2008.
6 * Copyright 2008 Google UK. All rights reserved.
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
21 #include "BitMatrix.h"
22 #include "IllegalArgumentException.h"
28 static unsigned int logDigits(unsigned digits) {
31 while (val < digits) {
38 static const unsigned int bitsPerWord_ =
39 numeric_limits<unsigned int>::digits;
40 static const unsigned int logBits_ = logDigits(bitsPerWord_);
41 static const unsigned int bitsMask_ = (1 << logBits_) - 1;
43 static size_t wordsForDimension(size_t dimension) {
44 size_t bits = dimension * dimension;
45 int arraySize = bits >> logBits_;
46 if (bits - (arraySize << logBits_) != 0) {
52 BitMatrix::BitMatrix(size_t dimension) :
53 dimension_(dimension), bits_(wordsForDimension(dimension)) {
56 BitMatrix::~BitMatrix() {
60 bool BitMatrix::get(size_t i, size_t j) {
61 size_t offset = i + dimension_ * j;
62 return ((bits_[offset >> logBits_] >> (offset & bitsMask_)) & 0x01) != 0;
65 void BitMatrix::set(size_t i, size_t j) {
66 size_t offset = i + dimension_ * j;
67 bits_[offset >> logBits_] |= 1 << (offset & bitsMask_);
70 void BitMatrix::setRegion(size_t topI,
74 if (topI < 0 || leftJ < 0) {
75 throw new IllegalArgumentException("topI and leftJ must be nonnegative");
77 if (height < 1 || width < 1) {
78 throw new IllegalArgumentException("height and width must be at least 1");
80 size_t maxJ = leftJ + width;
81 size_t maxI = topI + height;
82 if (maxI > dimension_ || maxJ > dimension_) {
83 throw new IllegalArgumentException
84 ("topI + height and leftJ + width must be <= matrix dimension");
86 for (size_t j = leftJ; j < maxJ; j++) {
87 int jOffset = dimension_ * j;
88 for (size_t i = topI; i < maxI; i++) {
89 size_t offset = i + jOffset;
90 bits_[offset >> logBits_] |= 1 << (offset & bitsMask_);
95 size_t BitMatrix::getDimension() {
99 valarray<unsigned int> &BitMatrix::getBits() {
103 ostream& operator<<(ostream &out, BitMatrix &bm) {
104 for (size_t i = 0; i < bm.dimension_; i++) {
105 for (size_t j = 0; j < bm.dimension_; j++) {
106 out << (bm.get(i, j) ? "* " : "- ");
112 const char *BitMatrix::description() {
115 return out.str().c_str();