home *** CD-ROM | disk | FTP | other *** search
/ Geek Gadgets 1 / ADE-1.bin / ade-dist / libg++-2.7.1-bin.lha / lib / g++-include / BitString.h < prev    next >
C/C++ Source or Header  |  1996-10-12  |  20KB  |  764 lines

  1. // This may look like C code, but it is really -*- C++ -*-
  2. /* 
  3. Copyright (C) 1988 Free Software Foundation
  4.     written by Doug Lea (dl@rocky.oswego.edu)
  5.  
  6. This file is part of the GNU C++ Library.  This library is free
  7. software; you can redistribute it and/or modify it under the terms of
  8. the GNU Library General Public License as published by the Free
  9. Software Foundation; either version 2 of the License, or (at your
  10. option) any later version.  This library is distributed in the hope
  11. that it will be useful, but WITHOUT ANY WARRANTY; without even the
  12. implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
  13. PURPOSE.  See the GNU Library General Public License for more details.
  14. You should have received a copy of the GNU Library General Public
  15. License along with this library; if not, write to the Free Software
  16. Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
  17. */
  18.  
  19. #ifndef _BitString_h
  20. #ifdef __GNUG__
  21. #pragma interface
  22. #endif
  23.  
  24. #define _BitString_h 1
  25.  
  26. #include <stream.h>
  27. #include <limits.h>
  28.  
  29. #undef OK
  30.  
  31. #include <bitprims.h>
  32. #define BITSTRBITS  _BS_BITS_PER_WORD
  33.  
  34. struct BitStrRep
  35. {
  36.   unsigned int    len;          // length in bits
  37.   unsigned short  sz;           // allocated slots
  38.   _BS_word        s[1];         // bits start here
  39. };
  40.  
  41. extern BitStrRep*  BStr_alloc(BitStrRep*, const _BS_word*, int, int,int);
  42. extern BitStrRep*  BStr_resize(BitStrRep*, int);
  43. extern BitStrRep*  BStr_copy(BitStrRep*, const BitStrRep*);
  44. extern BitStrRep*  cmpl(const BitStrRep*, BitStrRep*);
  45. extern BitStrRep*  and(const BitStrRep*, const BitStrRep*, BitStrRep*);
  46. extern BitStrRep*  or(const BitStrRep*, const BitStrRep*, BitStrRep*);
  47. extern BitStrRep*  xor(const BitStrRep*, const BitStrRep*, BitStrRep*);
  48. extern BitStrRep*  diff(const BitStrRep*, const BitStrRep*, BitStrRep*);
  49. extern BitStrRep*  cat(const BitStrRep*, const BitStrRep*, BitStrRep*);
  50. extern BitStrRep*  cat(const BitStrRep*, unsigned int, BitStrRep*);
  51. extern BitStrRep*  lshift(const BitStrRep*, int, BitStrRep*);
  52.  
  53.  
  54. class BitString;
  55. class BitPattern;
  56.  
  57. class BitStrBit
  58. {
  59. protected:
  60.   BitString&        src;
  61.   unsigned int      pos;
  62.  
  63.  public:
  64.                     BitStrBit(BitString& v, int p);
  65.                     BitStrBit(const BitStrBit& b);
  66.                    ~BitStrBit();
  67.                     operator unsigned int() const;
  68.   int               operator =  (unsigned int b);
  69. };
  70.  
  71. class BitSubString
  72. {
  73.   friend class      BitString;
  74.   friend class      BitPattern;
  75.  
  76. protected:
  77.  
  78.   BitString&        S;
  79.   unsigned int      pos;
  80.   unsigned int      len;
  81.  
  82.                     BitSubString(BitString& x, int p, int l);
  83.                     BitSubString(const BitSubString& x);
  84. public:
  85.                     ~BitSubString();
  86.  
  87.   BitSubString&     operator =  (const BitString&);
  88.   BitSubString&     operator =  (const BitSubString&);
  89.  
  90.   int               length() const;
  91.   int               empty() const;
  92.  
  93.   int               OK() const;
  94. };
  95.  
  96. class BitString
  97. {
  98.   friend class       BitSubString;
  99.   friend class       BitPattern;
  100. protected:
  101.   BitStrRep*         rep;
  102.  
  103.   int                search(int, int, const _BS_word*, int, int) const;
  104.   int                match(int, int, int, const _BS_word*,int,int) const;
  105.   BitSubString       _substr(int first, int l);
  106.  
  107. public:
  108.  
  109. // constructors
  110.                      BitString();
  111.                      BitString(const BitString&);
  112.                      BitString(const BitSubString& y);
  113.  
  114.                     ~BitString();
  115.  
  116.   BitString&         operator =  (unsigned int bit);
  117.   BitString&         operator =  (const BitString& y);
  118.   BitString&         operator =  (const BitSubString& y);
  119.  
  120. // equality & subset tests
  121.  
  122.   friend int         operator == (const BitString&, const BitString&);
  123.   friend int         operator != (const BitString&, const BitString&);
  124.   friend int         operator <  (const BitString&, const BitString&);
  125.   friend int         operator <= (const BitString&, const BitString&);
  126.   friend int         operator >  (const BitString&, const BitString&);
  127.   friend int         operator >= (const BitString&, const BitString&);
  128.  
  129. // procedural versions of operators
  130.  
  131.  
  132.   friend void        and(const BitString&, const BitString&, BitString&);
  133.   friend void        or(const BitString&, const BitString&, BitString&);
  134.   friend void        xor(const BitString&, const BitString&, BitString&);
  135.   friend void        diff(const BitString&, const BitString&, BitString&);
  136.   friend void        cat(const BitString&, const BitString&, BitString&);
  137.   friend void        cat(const BitString&, unsigned int, BitString&);
  138.   friend void        lshift(const BitString&, int, BitString&);
  139.   friend void        rshift(const BitString&, int, BitString&);
  140.  
  141.   friend void        complement(const BitString&, BitString&);
  142.  
  143.   friend int         lcompare(const BitString&, const BitString&); 
  144.  
  145. // assignment-based operators
  146. // (constuctive versions decalred inline below
  147.  
  148.   BitString&         operator |= (const BitString&);
  149.   BitString&         operator &= (const BitString&);
  150.   BitString&         operator -= (const BitString&);
  151.   BitString&         operator ^= (const BitString&);
  152.   BitString&         operator += (const BitString&);
  153.   BitString&         operator += (unsigned int b);
  154.   BitString&         operator <<=(int s);
  155.   BitString&         operator >>=(int s);
  156.  
  157.   void               complement();
  158.  
  159. // individual bit manipulation
  160.  
  161.   void               set(int pos);
  162.   void               set(int from, int to);
  163.   void               set();
  164.  
  165.   void               clear(int pos);
  166.   void               clear(int from, int to);
  167.   void               clear(); 
  168.  
  169.   void               invert(int pos);
  170.   void               invert(int from, int to);
  171.  
  172.   int                test(int pos) const;
  173.   int                test(int from, int to) const;
  174.  
  175.   void               assign(int p, unsigned int bit);
  176.  
  177. // indexing
  178.  
  179.   BitStrBit          operator [] (int pos);
  180.  
  181. // iterators
  182.  
  183.   int                first(unsigned int bit = 1) const;
  184.   int                last(unsigned int b = 1) const;
  185.  
  186.   int                next(int pos, unsigned int b = 1) const;
  187.   int                prev(int pos, unsigned int b = 1) const;
  188.   int                previous(int pos, unsigned int b = 1) const
  189.     { return prev(pos, b); } /* Obsolete synonym */
  190.  
  191. // searching & matching
  192.  
  193.   int                index(unsigned int bit, int startpos = 0) const ;      
  194.   int                index(const BitString&, int startpos = 0) const;
  195.   int                index(const BitSubString&, int startpos = 0) const;
  196.   int                index(const BitPattern&, int startpos = 0) const;
  197.  
  198.   int                contains(const BitString&) const;
  199.   int                contains(const BitSubString&) const;
  200.   int                contains(const BitPattern&) const;
  201.  
  202.   int                contains(const BitString&, int pos) const;
  203.   int                contains(const BitSubString&, int pos) const;
  204.   int                contains(const BitPattern&, int pos) const;
  205.  
  206.   int                matches(const BitString&, int pos = 0) const;
  207.   int                matches(const BitSubString&, int pos = 0) const;
  208.   int                matches(const BitPattern&, int pos = 0) const;
  209.  
  210. // BitSubString extraction
  211.  
  212.   BitSubString       at(int pos, int len);
  213.   BitSubString       at(const BitString&, int startpos = 0); 
  214.   BitSubString       at(const BitSubString&, int startpos = 0); 
  215.   BitSubString       at(const BitPattern&, int startpos = 0); 
  216.  
  217.   BitSubString       before(int pos);
  218.   BitSubString       before(const BitString&, int startpos = 0);
  219.   BitSubString       before(const BitSubString&, int startpos = 0);
  220.   BitSubString       before(const BitPattern&, int startpos = 0);
  221.  
  222.   BitSubString       after(int pos);
  223.   BitSubString       after(const BitString&, int startpos = 0);
  224.   BitSubString       after(const BitSubString&, int startpos = 0);
  225.   BitSubString       after(const BitPattern&, int startpos = 0);
  226.  
  227. // other friends & utilities
  228.  
  229.   friend BitString   common_prefix(const BitString&, const BitString&, 
  230.                                    int pos = 0);
  231.   friend BitString   common_suffix(const BitString&, const BitString&, 
  232.                                    int pos = -1);
  233.   friend BitString   reverse(const BitString&);
  234.  
  235.   void               right_trim(unsigned int bit);
  236.   void               left_trim(unsigned int bit);
  237.  
  238. // status
  239.  
  240.   int                empty() const ;
  241.   int                count(unsigned int bit = 1) const;
  242.   int                length() const;
  243.  
  244. // convertors & IO
  245.  
  246.   friend BitString   atoBitString(const char* s, char f='0', char t='1');
  247.   // BitStringtoa is deprecated; do not use in new programs!
  248.   friend const char* BitStringtoa(const BitString&, char f='0', char t='1');
  249.   void             printon(ostream&, char f='0', char t='1') const;
  250.  
  251.   friend BitString   shorttoBitString(unsigned short);
  252.   friend BitString   longtoBitString(unsigned long);
  253.  
  254.   friend ostream&    operator << (ostream& s, const BitString&);
  255.  
  256. // misc
  257.  
  258.   void      error(const char* msg) const;
  259.  
  260. // indirect friends
  261.  
  262.   friend BitPattern  atoBitPattern(const char* s,
  263.                                   char f='0',char t='1',char x='X');
  264.   friend const char* BitPatterntoa(const BitPattern& p, 
  265.                                   char f='0',char t='1',char x='X');
  266.   int                OK() const;
  267. };
  268.  
  269.  
  270. class BitPattern
  271. {
  272. public:
  273.   BitString          pattern;
  274.   BitString          mask;
  275.  
  276.                      BitPattern();
  277.                      BitPattern(const BitPattern&);
  278.                      BitPattern(const BitString& p, const BitString& m);
  279.  
  280.                     ~BitPattern();
  281.  
  282.   friend const char* BitPatterntoa(const BitPattern& p, 
  283.                                  char f/*='0'*/,char t/*='1'*/,char x/*='X'*/);
  284.   void             printon(ostream&, char f='0',char t='1',char x='X') const;
  285.   friend BitPattern atoBitPattern(const char* s, char f,char t, char x);
  286.   friend ostream&   operator << (ostream& s, const BitPattern&);
  287.  
  288.   int               search(const _BS_word*, int, int) const;
  289.   int               match(const _BS_word* xs, int, int, int) const;
  290.  
  291.   int               OK() const;
  292. };
  293.  
  294. BitString  operator & (const BitString& x, const BitString& y);
  295. BitString  operator | (const BitString& x, const BitString& y);
  296. BitString  operator ^ (const BitString& x, const BitString& y);
  297. BitString  operator << (const BitString& x, int y);
  298. BitString  operator >> (const BitString& x, int y);
  299. BitString  operator - (const BitString& x, const BitString& y);
  300. BitString  operator + (const BitString& x, const BitString& y);
  301. BitString  operator + (const BitString& x, unsigned int y);
  302. BitString  operator ~ (const BitString& x);
  303. int operator != (const BitString& x, const BitString& y);
  304. int operator>(const BitString& x, const BitString& y);
  305. int operator>=(const BitString& x, const BitString& y);
  306.  
  307. extern BitStrRep    _nilBitStrRep;
  308. extern BitString    _nil_BitString;
  309.  
  310. // primitive bit extraction
  311.  
  312. // These must be inlined regardless of optimization.
  313.  
  314. inline int BitStr_index(int l) { return (unsigned)(l) / BITSTRBITS; }
  315.  
  316. inline int BitStr_pos(int l) { return l & (BITSTRBITS - 1); }
  317.  
  318.  
  319. // constructors & assignment
  320.  
  321. inline BitString::BitString() :rep(&_nilBitStrRep) {}
  322.  
  323. inline BitString::BitString(const BitString& x) :rep(BStr_copy(0, x.rep)) {}
  324.  
  325. inline BitString::BitString(const BitSubString& y) 
  326.    :rep (BStr_alloc(0, y.S.rep->s, y.pos, y.pos+y.len, y.len)) {}
  327.  
  328. inline BitString::~BitString()
  329.   if (rep != &_nilBitStrRep) delete rep;
  330. }
  331.  
  332. inline BitString shorttoBitString(unsigned short w) 
  333.   BitString r;
  334.   _BS_word ww = w;
  335. #if _BS_BIGENDIAN
  336.   abort();
  337. #endif
  338.   r.rep = BStr_alloc(0, &ww, 0, 8 * sizeof(short), 8 * sizeof(short));
  339.   return r;
  340. }
  341.  
  342. inline BitString longtoBitString(unsigned long w) 
  343.   BitString r;
  344. #if 1
  345.   _BS_word u = w;
  346.   r.rep = BStr_alloc(0, &u, 0, BITSTRBITS, BITSTRBITS);
  347. #else
  348.   unsigned short u[2];
  349.   u[0] = w & ((unsigned short)(~(0)));
  350.   u[1] = w >> BITSTRBITS;
  351.   r.rep = BStr_alloc(0, &u[0], 0, 2*BITSTRBITS, 2*BITSTRBITS);
  352. #endif
  353.   return r;
  354. }
  355.  
  356. inline BitString& BitString::operator =  (const BitString& y)
  357.   rep = BStr_copy(rep, y.rep);
  358.   return *this;
  359. }
  360.  
  361. inline BitString& BitString::operator = (unsigned int b)
  362.   _BS_word bit = b;
  363.   rep = BStr_alloc(rep, &bit, 0, 1, 1);
  364.   return *this;
  365. }
  366.  
  367. inline BitString&  BitString::operator=(const BitSubString&  y)
  368. {
  369.   rep = BStr_alloc(rep, y.S.rep->s, y.pos, y.pos+y.len, y.len);
  370.   return *this;
  371. }
  372.  
  373. inline BitSubString::BitSubString(const BitSubString& x) 
  374.     :S(x.S), pos(x.pos), len(x.len) {}
  375.  
  376. inline BitSubString::BitSubString(BitString& x, int p, int l)
  377.      : S(x), pos(p), len(l) {}
  378.  
  379. inline BitSubString::~BitSubString() {}
  380.  
  381. inline BitPattern::BitPattern(const BitString& p, const BitString& m)
  382.     :pattern(p), mask(m) {}
  383.  
  384. inline BitPattern::BitPattern(const BitPattern& b)
  385.     :pattern(b.pattern), mask(b.mask) {}
  386.  
  387. inline BitPattern::BitPattern() {}
  388. inline BitPattern::~BitPattern() {}
  389.  
  390.  
  391. // procedural versions of operators
  392.  
  393. inline void and(const BitString& x, const BitString& y, BitString& r)
  394. {
  395.   r.rep = and(x.rep, y.rep, r.rep);
  396. }
  397.  
  398. inline void or(const BitString& x, const BitString& y, BitString& r)
  399. {
  400.   r.rep = or(x.rep, y.rep, r.rep);
  401. }
  402.  
  403. inline void xor(const BitString& x, const BitString& y, BitString& r)
  404. {
  405.   r.rep = xor(x.rep, y.rep, r.rep);
  406. }
  407.  
  408. inline void diff(const BitString& x, const BitString& y, BitString& r)
  409. {
  410.   r.rep = diff(x.rep, y.rep, r.rep);
  411. }
  412.  
  413. inline void cat(const BitString& x, const BitString& y, BitString& r)
  414. {
  415.   r.rep = cat(x.rep, y.rep, r.rep);
  416. }
  417.  
  418. inline void cat(const BitString& x, unsigned int y, BitString& r)
  419. {
  420.   r.rep = cat(x.rep, y, r.rep);
  421. }
  422.  
  423. inline void rshift(const BitString& x, int y, BitString& r)
  424. {
  425.   r.rep = lshift(x.rep, -y, r.rep);
  426. }
  427.  
  428. inline void lshift(const BitString& x, int y, BitString& r)
  429. {
  430.   r.rep = lshift(x.rep, y, r.rep);
  431. }
  432.  
  433. inline void complement(const BitString& x, BitString& r)
  434. {
  435.   r.rep = cmpl(x.rep, r.rep);
  436. }
  437.  
  438. // operators
  439.  
  440.  
  441. inline BitString& BitString::operator &= (const BitString& y)
  442. {
  443.   and(*this, y, *this);
  444.   return *this;
  445. }
  446.  
  447.  
  448. inline BitString& BitString::operator |= (const BitString& y)
  449. {
  450.   or(*this, y, *this);
  451.   return *this;
  452. }
  453.  
  454. inline BitString& BitString::operator ^= (const BitString& y)
  455. {
  456.   xor(*this, y, *this);
  457.   return *this;
  458. }
  459.  
  460. inline BitString& BitString::operator <<= (int y)
  461. {
  462.   lshift(*this, y, *this);
  463.   return *this;
  464. }
  465.  
  466. inline BitString& BitString::operator >>= (int y)
  467. {
  468.   rshift(*this, y, *this);
  469.   return *this;
  470. }
  471.  
  472. inline BitString& BitString::operator -= (const BitString& y)
  473. {
  474.   diff(*this, y, *this);
  475.   return *this;
  476. }
  477.  
  478. inline BitString& BitString::operator += (const BitString& y)
  479. {
  480.   cat(*this, y, *this);
  481.   return *this;
  482. }
  483.  
  484. inline BitString& BitString::operator += (unsigned int y)
  485. {
  486.   cat(*this, y, *this);
  487.   return *this;
  488. }
  489.  
  490. inline void BitString::complement()
  491. {
  492.   ::complement(*this, *this);
  493. }
  494.  
  495. #if defined(__GNUG__) && !defined(_G_NO_NRV)
  496.  
  497. inline BitString  operator & (const BitString& x, const BitString& y) return r
  498. {
  499.   and(x, y, r);
  500. }
  501.  
  502. inline BitString  operator | (const BitString& x, const BitString& y) return r
  503. {
  504.   or(x, y, r);
  505. }
  506.  
  507. inline BitString  operator ^ (const BitString& x, const BitString& y) return r
  508. {
  509.   xor(x, y, r);
  510. }
  511.  
  512. inline BitString  operator << (const BitString& x, int y) return r
  513. {
  514.   lshift(x, y, r);
  515. }
  516.  
  517. inline BitString  operator >> (const BitString& x, int y) return r
  518. {
  519.   rshift(x, y, r);
  520. }
  521.  
  522. inline BitString  operator - (const BitString& x, const BitString& y) return r
  523. {
  524.   diff(x, y, r);
  525. }
  526.  
  527. inline BitString  operator + (const BitString& x, const BitString& y) return r
  528. {
  529.   cat(x, y, r);
  530. }
  531.  
  532. inline BitString  operator + (const BitString& x, unsigned int y) return r
  533. {
  534.   cat(x, y, r);
  535. }
  536.  
  537. inline BitString  operator ~ (const BitString& x) return r
  538. {
  539.   complement(x, r);
  540. }
  541.  
  542. #else /* NO_NRV */
  543.  
  544. inline BitString  operator & (const BitString& x, const BitString& y) 
  545. {
  546.   BitString r; and(x, y, r); return r;
  547. }
  548.  
  549. inline BitString  operator | (const BitString& x, const BitString& y) 
  550. {
  551.   BitString r; or(x, y, r); return r;
  552. }
  553.  
  554. inline BitString  operator ^ (const BitString& x, const BitString& y) 
  555. {
  556.   BitString r; xor(x, y, r); return r;
  557. }
  558.  
  559. inline BitString  operator << (const BitString& x, int y) 
  560. {
  561.   BitString r; lshift(x, y, r); return r;
  562. }
  563.  
  564. inline BitString  operator >> (const BitString& x, int y) 
  565. {
  566.   BitString r; rshift(x, y, r); return r;
  567. }
  568.  
  569. inline BitString  operator - (const BitString& x, const BitString& y) 
  570. {
  571.   BitString r; diff(x, y, r); return r;
  572. }
  573.  
  574. inline BitString  operator + (const BitString& x, const BitString& y) 
  575. {
  576.   BitString r; cat(x, y, r); return r;
  577. }
  578.  
  579. inline BitString  operator + (const BitString& x, unsigned int y) 
  580. {
  581.   BitString r; cat(x, y, r); return r;
  582. }
  583.  
  584. inline BitString  operator ~ (const BitString& x) 
  585. {
  586.   BitString r; complement(x, r); return r;
  587. }
  588.  
  589. #endif
  590.  
  591. // status, matching
  592.  
  593. inline int BitString::length() const
  594.   return rep->len;
  595. }
  596.  
  597. inline int BitString::empty() const
  598.   return rep->len == 0;
  599. }
  600.  
  601. inline int BitString::index(const BitString& y, int startpos) const
  602. {   
  603.   return search(startpos, rep->len, y.rep->s, 0, y.rep->len);
  604. }
  605.  
  606. inline int BitString::index(const BitSubString& y, int startpos) const
  607. {   
  608.   return search(startpos, rep->len, y.S.rep->s, y.pos, y.pos+y.len);
  609. }
  610.  
  611. inline int BitString::contains(const BitString& y) const
  612. {   
  613.   return search(0, rep->len, y.rep->s, 0, y.rep->len) >= 0;
  614. }
  615.  
  616. inline int BitString::contains(const BitSubString& y) const
  617. {   
  618.   return search(0, rep->len, y.S.rep->s, y.pos, y.pos+y.len) >= 0;
  619. }
  620.  
  621. inline int BitString::contains(const BitString& y, int p) const
  622. {
  623.   return match(p, rep->len, 0, y.rep->s, 0, y.rep->len);
  624. }
  625.  
  626. inline int BitString::matches(const BitString& y, int p) const
  627. {
  628.   return match(p, rep->len, 1, y.rep->s, 0, y.rep->len);
  629. }
  630.  
  631. inline int BitString::contains(const BitSubString& y, int p) const
  632. {
  633.   return match(p, rep->len, 0, y.S.rep->s, y.pos, y.pos+y.len);
  634. }
  635.  
  636. inline int BitString::matches(const BitSubString& y, int p) const
  637. {
  638.   return match(p, rep->len, 1, y.S.rep->s, y.pos, y.pos+y.len);
  639. }
  640.  
  641. inline int BitString::contains(const BitPattern& r) const
  642. {
  643.   return r.search(rep->s, 0, rep->len) >= 0;
  644. }
  645.  
  646. inline int BitString::contains(const BitPattern& r, int p) const
  647. {
  648.   return r.match(rep->s, p, rep->len, 0);
  649. }
  650.  
  651. inline int BitString::matches(const BitPattern& r, int p) const
  652. {
  653.   return r.match(rep->s, p, rep->len, 1);
  654. }
  655.  
  656. inline int BitString::index(const BitPattern& r, int startpos) const
  657. {
  658.   return r.search(rep->s, startpos, rep->len);
  659. }
  660.  
  661. inline  int BitSubString::length() const
  662.   return len;
  663. }
  664.  
  665. inline  int BitSubString::empty() const
  666.   return len == 0;
  667. }
  668.  
  669. inline int operator != (const BitString& x, const BitString& y)
  670. {
  671.   return !(x == y);
  672. }
  673.  
  674. inline int operator>(const BitString& x, const BitString& y)
  675. {
  676.   return y < x;
  677. }
  678.  
  679. inline int operator>=(const BitString& x, const BitString& y)
  680. {
  681.   return y <= x;
  682. }
  683.  
  684. inline int BitString::first(unsigned int b) const
  685. {
  686.   return next(-1, b);
  687. }
  688.  
  689. inline int BitString::last(unsigned int b) const
  690. {
  691.   return prev(rep->len, b);
  692. }
  693.  
  694. inline int BitString::index(unsigned int bit, int startpos) const
  695. {
  696.   if (startpos >= 0)
  697.     return next(startpos - 1, bit);
  698.   else
  699.     return prev(rep->len + startpos + 1, bit);
  700. }
  701.  
  702. inline void BitString::right_trim(unsigned int b) 
  703. {
  704.   int nb = (b == 0)? 1 : 0;
  705.   rep = BStr_resize(rep, prev(rep->len, nb) + 1);
  706. }
  707.  
  708. inline void BitString::left_trim(unsigned int b)
  709. {
  710.   int nb = (b == 0)? 1 : 0;
  711.   int p = next(-1, nb);
  712.   rep = BStr_alloc(rep, rep->s, p, rep->len, rep->len - p);
  713. }
  714.  
  715. inline int BitString::test(int i) const
  716. {
  717.   return ((unsigned)(i) >= rep->len)? 0 : 
  718.          ((rep->s[BitStr_index(i)] & (1 << (BitStr_pos(i)))) != 0);
  719. }
  720.  
  721.  
  722. // subscripting
  723.  
  724. inline BitStrBit::BitStrBit(const BitStrBit& b) :src(b.src), pos(b.pos) {}
  725.  
  726. inline BitStrBit::BitStrBit(BitString& v, int p) :src(v), pos(p) {}
  727.  
  728. inline BitStrBit::~BitStrBit() {}
  729.  
  730. inline BitStrBit::operator unsigned int() const
  731. {
  732.   return src.test(pos);
  733. }
  734.  
  735. inline int BitStrBit::operator = (unsigned int b)
  736. {
  737.   src.assign(pos, b); return b;
  738. }
  739.  
  740. inline BitStrBit BitString::operator [] (int i)
  741. {
  742.   if ((unsigned)(i) >= rep->len) error("illegal bit index");
  743.   return BitStrBit(*this, i);
  744. }
  745.  
  746. inline BitSubString BitString::_substr(int first, int l)
  747. {
  748.   if (first < 0 || l <= 0 || (unsigned)(first + l) > rep->len)
  749.     return BitSubString(_nil_BitString, 0, 0) ;
  750.   else 
  751.     return BitSubString(*this, first, l);
  752. }
  753.  
  754. #endif
  755.