CSS product code  0.1
C++ library to estimate distance of CSS codes. Some particular construction of CSS codes are implemented.
bp.cpp
Go to the documentation of this file.
1 //Weilei Zeng, April 28
2 //return min weight of rows in C, which is the distance of the code
3 //random window method is applied with default number of permutation 10.
4 
5 //#include "weilei_lib/my_lib.h"
6 #include "dist.h"
7 #include <itpp/itbase.h>
8 #include <itpp/itcomm.h>
9 #include <stdio.h>
10 #include "weilei_lib.h"
11 #include <cmath>
12 
13 
14 
15 
16 itpp::bvec reduce_weight(itpp::bvec e, itpp::GF2mat G){
17  //reduce the weight of en error vector e, G include all cycles (equivalent error). G is assument to be the generator matrix of an Quantum LDPC CSS code. such that rows of G correspond to the smallest cycles. It is assument that e is an effectively small/zero weight error, which contains many trivial cycles. This function will reduce most of those small individual cycles so that we can count the effective weight of e.
18  // complexity of this program: ~ G.rows() * weight(e)
19  int row=G.rows();
20  bool converge = false;
21  itpp::bvec e1;
22  int wt=weight(e);
23  while (! converge){
24  converge=true;//assume it is already at min weight
25  for (int i =0; i< row;i++){
26  e1=e+G.get_row(i);
27  if (weight(e1) < wt){
28  e=e1;
29  wt=weight(e1);
30  converge = false;
31  }
32  }
33  }
34  return e;
35 }
36 
37 
38 itpp::bvec qllr_to_bvec(itpp::QLLRvec llr, int bound){
39  //find the appropriate bound value and return binary vector from this qllr.
40  //Its sign is the same as the sign of "bound"
41  /*
42  int bound1=bound;
43  int m = max( abs(llr));
44  int upper = m/100;
45  int lower = m/10000;
46  bound1=min(upper,bound1);
47  bound1=max(lower,bound1);
48  bound1 = bound / abs(bound) *bound1;
49 
50  bound1=0;
51  itpp::bvec bits_out = llr < bound1;
52 
53  std::cout<<"actual bound1 = "<<bound1<<std::endl;
54  return bits_out;
55  */
56  itpp::bvec bits_out = llr <0;
57  return bits_out;
58 }
59 
60 
61 //for partial sum project
62 
63 itpp::GF2mat read_one_matrix(char * filename_prefix, char * type, char * filename_suffix){
64 
65  char filename[255];
66  sprintf( filename,"%s%s%s",filename_prefix, type, filename_suffix);//append p in the file name
67  //std::cout<<"read one itpp::matrix: "<<filename<<std::endl;
68  return MM_to_GF2mat(filename);
69 }
70 
71 
72 int check_matrices(itpp::GF2mat * G, itpp::GF2mat * H, itpp::GF2mat *U, itpp::GF2mat * W, itpp::mat * K){
73  //check if those matrices are valid
74  //it seems that H has some weight 1 column, which is not permited in H. bugs find when weight =7, size =9 or 13
75  std::cout<<"debug read matrices by checking some relation of the output matrices"<<std::endl;
76  // GF2matPrint(*G,"G");
77  common::GF2matPrint(*G,(char *) "G");
78  common::GF2matPrint(*H,(char *) "H");
79  common::GF2matPrint(*U,(char *) "U");
80  common::GF2matPrint(*W,(char *) "W");
81  common::matPrint(*K,(char *) "K");
82 
83  std::cout<<"if G*H is zero? ->"<<( ( *G * (*H).transpose()).is_zero() ?"yes":"no" )<<std::endl;
84 
85  if ( G->cols() == H->cols() && G->cols()==U->cols() && G->cols() == K->cols()-1 && G->rows() == W->rows() ){
86  std::cout<<"dimension matches"<<std::endl;
87  }else{
88  std::cout<<"dimension does NOT match"<<std::endl;
89  }
90 
91 
92  //check column weight of H, variable to check nodes require min wt >=1
93  for ( int i =0; i< H->cols();i++){
94  int wt=0;
95  for ( int j=0;j<H->rows();j++)
96  if ( H->get(j,i) ) wt++;
97  if ( wt < 1)
98  std::cout<<"find column wt < 1 in H. column index "<<i<<" wt = "<<wt<<std::endl;
99  }
100  //check row weight of H. check to variable nodes require min wt >=2
101  for ( int i =0; i< H->rows();i++){
102  int wt=0;
103  for ( int j=0;j<H->cols();j++)
104  if ( H->get(i,j) ) wt++;
105  if ( wt < 2)
106  std::cout<<"find row wt < 2 in H. column index "<<i<<" wt = "<<wt<<std::endl;
107  }
108  std::cout<<H -> rows()<<" row rank "<<H->row_rank()<<std::endl;
109 
110  //check min weight of G
111  int d = common::rand_dist(*G);
112  std::cout<< "min weight of G: "<<d<<std::endl;
113  std::cout<<"finish checking matrices"<<std::endl;
114  return 0;
115 }
116 
117 int remove_rows(itpp::GF2mat *G, itpp::bvec rows_to_remove){
118  //remove row in G, corresponding to one in itpp::bvec rows_to_remove
119  int rows=G->rows(), cols=G->cols();
120  itpp::ivec perm(rows);
121  int t=0;
122  // std::cout<<perm<<std::endl;
123  for ( int i =0; i<rows;i++){
124  if (rows_to_remove(rows-i-1)){
125  perm(rows-1-t)= rows-i-1;
126  t++;
127  }
128  }
129  // std::cout<<"t = "<<t<<std::endl;
130  //std::cout<<perm<<std::endl;
131  int t1=0;
132  for (int i = 0; i< rows;i++){
133  if (rows_to_remove(rows-i-1)){
134  t1++;
135  }
136  //perm(rows-i-t-1)=rows-i+t-t1;
137  else{
138  perm(rows-i-t-1+t1)=rows-i-1;
139  }
140  // std::cout<<i<<std::endl;
141  //std::cout<<perm<<std::endl;
142  }
143  G->permute_rows(perm,false);//true or false
144  G->set_size(rows-t,cols,true);
145  return 0 ;
146 }
147 
148 int remove_cols(itpp::GF2mat *G, itpp::bvec cols_to_remove){
149  itpp::GF2mat H = G->transpose();
150  remove_rows(&H, cols_to_remove);
151 
152  itpp::GF2mat H1 = H.transpose();
153  *G = H1;
154  return 0;
155 }
156 
157 int remove_cols_mat(itpp::mat *G, itpp::bvec cols_to_remove){
158  //have to write a seperate one for K
159  int size = cols_to_remove.size();
160  int t=0;
161  for ( int i = size-1; i>-1;i--){
162  if ( cols_to_remove(i) ){
163  for ( int j=i;j<size-t-1;j++){
164  G->swap_cols(j,j+1);
165  }
166  t++;
167  }
168  }
169  int rows=G->rows(),cols=G->cols();
170  G->set_size(rows,cols-t,true);
171  return 0;
172 }
173 
174 //return true if H has row with weight 1. not in use
175 bool check_row_weight(itpp::GF2mat *H){
176  for ( int i =0; i< H->rows();i++){
177  int wt=0;
178  for ( int j=0;j<H->cols();j++)
179  if ( H->get(i,j) ) wt++;
180  if ( wt < 2){
181  // std::cout<<"find row wt < 2 in H. row index "<<i<<" wt = "<<wt<<std::endl;
182  return true;
183  }
184  }
185  return false;
186 }
187 
188 //remove rows with weight one in H, and fix other matrices
189 int reduce_matrices( itpp::GF2mat * G, itpp::GF2mat * H, itpp::GF2mat *U, itpp::GF2mat * W, itpp::mat * K){
190  //now remove weight one rows in H by removing corresponding column in H and other matrices.
191 
192  //check row weight of H. check to variable nodes require min wt >=2
193  //std::cout<<"start removing columns"<<std::endl;
194  itpp::bvec columns_to_remove = itpp::zeros_b(H->cols());
195  int rt=0;//,ct=0; //rows_to_remove_count=0; columns_to_remove_count=0
196  itpp::bvec rows_to_remove = itpp::zeros_b(H->rows());
197  for ( int i =0; i< H->rows();i++){
198  int wt=0;
199  for ( int j=0;j<H->cols();j++)
200  if ( H->get(i,j) ) wt++;
201  if ( wt < 2){
202  // std::cout<<"find row wt < 2 in H. row index "<<i<<" wt = "<<wt<<std::endl;
203  rows_to_remove.set(i,1);
204  rt++;
205  for ( int j=0;j<H->cols();j++)
206  if ( H->get(i,j) ) columns_to_remove.set(j,1);
207  }
208  }
209 
210  if (rt>0){//remove columns if needed
211 
212  remove_rows(H,rows_to_remove); //try only remove rows
213 
214  /*
215  remove_cols(H,columns_to_remove);
216  remove_cols(G,columns_to_remove);
217  remove_cols(U,columns_to_remove);
218  remove_rows(H,rows_to_remove);
219  itpp::bvec columns_to_remove_K(1+columns_to_remove.size());
220  columns_to_remove_K.set_subvector(1,columns_to_remove);
221  columns_to_remove_K.set(0,0);
222  remove_cols_mat(K,columns_to_remove_K);
223  */
224  }
225  return 0;
226 }
227 
228 //for partial sum decoder
229 //read those matrices in the folder
230 int read_matrices_for_partial_sum(char * filename_prefix, char * filename_suffix, itpp::GF2mat * G, itpp::GF2mat * H, itpp::GF2mat *U, itpp::GF2mat * W, itpp::mat * K){
231 
232  *G = read_one_matrix(filename_prefix,(char *) "g",filename_suffix);
233  *H=read_one_matrix(filename_prefix,(char *) "h",filename_suffix);
234  *U=read_one_matrix(filename_prefix,(char *) "u",filename_suffix);
235  *W=read_one_matrix(filename_prefix,(char *) "w",filename_suffix);
236  //read K seperately because it is a mat other than a GF2mat
237  char filename[255];
238  sprintf( filename,"%s%s%s",filename_prefix, "K", filename_suffix);//append p in the file name
239  // std::cout<<filename<<std::endl;
240  *K = MM_to_mat(filename);
241 
242 
243  //*H=make_it_full_rank(*H); //not working yet, check it later
244 
245  //while ( check_row_weight(H) ) {
246  reduce_matrices(G, H,U, W, K);
247  //}
248  check_matrices(G, H,U, W, K);
249 
250  // itpp::GF2mat G0=MM_to_GF2mat( (char *) "mathematica/matrices/surf5_g_1.mtx" );
251 
252  return 0;
253 }
254 
common::matPrint
int matPrint(itpp::mat G, char *name=(char *) " ")
Definition: lib.cpp:153
read_one_matrix
itpp::GF2mat read_one_matrix(char *filename_prefix, char *type, char *filename_suffix)
Definition: bp.cpp:63
MM_to_mat
itpp::mat MM_to_mat(std::string file_name)
Definition: mm_read.cpp:42
remove_cols
int remove_cols(itpp::GF2mat *G, itpp::bvec cols_to_remove)
Definition: bp.cpp:148
qllr_to_bvec
itpp::bvec qllr_to_bvec(itpp::QLLRvec llr, int bound)
Definition: bp.cpp:38
MM_to_GF2mat
itpp::GF2mat MM_to_GF2mat(std::string file_name)
Definition: mm_read.cpp:36
weilei_lib.h
this file links all other headfiles in this folder.
reduce_weight
itpp::bvec reduce_weight(itpp::bvec e, itpp::GF2mat G)
Definition: bp.cpp:16
dist.h
distance related functions, defined within namespace common
remove_cols_mat
int remove_cols_mat(itpp::mat *G, itpp::bvec cols_to_remove)
Definition: bp.cpp:157
common::rand_dist
int rand_dist(itpp::GF2mat C, int perm_try=10)
Definition: dist.cpp:82
read_matrices_for_partial_sum
int read_matrices_for_partial_sum(char *filename_prefix, char *filename_suffix, itpp::GF2mat *G, itpp::GF2mat *H, itpp::GF2mat *U, itpp::GF2mat *W, itpp::mat *K)
Definition: bp.cpp:230
remove_rows
int remove_rows(itpp::GF2mat *G, itpp::bvec rows_to_remove)
Definition: bp.cpp:117
check_row_weight
bool check_row_weight(itpp::GF2mat *H)
Definition: bp.cpp:175
reduce_matrices
int reduce_matrices(itpp::GF2mat *G, itpp::GF2mat *H, itpp::GF2mat *U, itpp::GF2mat *W, itpp::mat *K)
Definition: bp.cpp:189
check_matrices
int check_matrices(itpp::GF2mat *G, itpp::GF2mat *H, itpp::GF2mat *U, itpp::GF2mat *W, itpp::mat *K)
Definition: bp.cpp:72
common::GF2matPrint
int GF2matPrint(itpp::GF2mat &G, std::string name)
Definition: lib.cpp:144