001/* 002 * $Id: ExpVectorTest.java 5688 2017-01-03 08:45:09Z kredel $ 003 */ 004 005package edu.jas.poly; 006 007 008import java.util.ArrayList; 009import java.util.Arrays; 010import java.util.List; 011 012import junit.framework.Test; 013import junit.framework.TestCase; 014import junit.framework.TestSuite; 015 016import org.apache.log4j.BasicConfigurator; 017 018import edu.jas.arith.BigInteger; 019 020 021/** 022 * ExpVector tests with JUnit. Tests arithmetic operations, for comparison tests 023 * see TermOrderTest. 024 * @author Heinz Kredel 025 */ 026 027public class ExpVectorTest extends TestCase { 028 029 030 /** 031 * main 032 */ 033 public static void main(String[] args) { 034 BasicConfigurator.configure(); 035 junit.textui.TestRunner.run(suite()); 036 } 037 038 039 /** 040 * Constructs a <CODE>ExpVectorTest</CODE> object. 041 * @param name String. 042 */ 043 public ExpVectorTest(String name) { 044 super(name); 045 } 046 047 048 /** 049 */ 050 public static Test suite() { 051 TestSuite suite = new TestSuite(ExpVectorTest.class); 052 return suite; 053 } 054 055 056 ExpVector a, b, c, d; 057 058 059 @Override 060 protected void setUp() { 061 a = b = c = d = null; 062 } 063 064 065 @Override 066 protected void tearDown() { 067 a = b = c = d = null; 068 } 069 070 071 /** 072 * Test constructor and toString. 073 */ 074 public void testConstructor() { 075 a = ExpVector.create(0); 076 b = ExpVector.create(0); 077 assertEquals("() = ()", a, b); 078 assertEquals("length( () ) = 0", a.length(), 0); 079 assertTrue("isZERO( () )", a.isZERO()); 080 081 a = ExpVector.create(10); 082 b = ExpVector.create(10); 083 assertEquals("10e = 10e", a, b); 084 assertEquals("length( 10e ) = 10", a.length(), 10); 085 assertTrue("isZERO( ( 10e ) )", a.isZERO()); 086 087 String s = "(0,0,0,0,0,0,0,0,0,0)"; 088 a = ExpVector.create(s); 089 String t = a.toString().substring(0, s.length()); 090 091 assertEquals("stringConstr = toString", s, t); 092 assertTrue("isZERO( ( 10e ) )", a.isZERO()); 093 } 094 095 096 /** 097 * Test bitLength. 098 */ 099 public void testBitLength() { 100 a = ExpVector.create(0); 101 assertEquals("blen(0) = 0", 0, a.bitLength()); 102 103 b = ExpVector.create(10); 104 assertEquals("blen(0) = 10", 10, b.bitLength()); 105 106 c = ExpVector.random(10, 20, 0.5f); 107 //System.out.println("c = " + c); 108 //System.out.println("blen(c) = " + c.bitLength()); 109 assertTrue("blen(random) >= 0", 0 <= c.bitLength()); 110 } 111 112 113 /** 114 * Test random integer. 115 */ 116 public void testRandom() { 117 float q = (float) 0.3; 118 119 a = ExpVector.EVRAND(5, 10, q); 120 String s = a.toString(); 121 if (s.indexOf(":") >= 0) { 122 s = s.substring(0, s.indexOf(":")); 123 } 124 b = ExpVector.create(s); 125 126 assertEquals("a == b", true, a.equals(b)); 127 128 c = ExpVector.EVDIF(b, a); 129 130 assertTrue("a-b = 0", c.isZERO()); 131 } 132 133 134 /** 135 * Test addition. 136 */ 137 public void testAddition() { 138 float q = (float) 0.2; 139 140 a = ExpVector.EVRAND(5, 10, q); 141 142 b = ExpVector.EVSUM(a, a); 143 c = ExpVector.EVDIF(b, a); 144 145 assertEquals("a+a-a = a", c, a); 146 assertTrue("a+a-a = a", c.equals(a)); 147 148 boolean t; 149 t = ExpVector.EVMT(b, a); 150 assertTrue("a | a+a", t); 151 152 a = ExpVector.EVRAND(5, 10, q); 153 b = ExpVector.EVRAND(5, 10, q); 154 155 c = ExpVector.EVSUM(a, b); 156 d = ExpVector.EVSUM(b, a); 157 assertTrue("a+b = b+a", c.equals(d)); 158 } 159 160 161 /** 162 * Test lcm. 163 */ 164 public void testLcm() { 165 float q = (float) 0.2; 166 167 a = ExpVector.EVRAND(5, 10, q); 168 b = ExpVector.EVRAND(5, 10, q); 169 c = ExpVector.EVLCM(a, b); 170 d = ExpVector.EVLCM(b, a); 171 172 assertTrue("lcm(a,b) = lcm(b,a)", c.equals(d)); 173 174 assertTrue("a | lcm(a,b)", ExpVector.EVMT(c, a)); 175 assertTrue("b | lcm(a,b)", ExpVector.EVMT(c, b)); 176 177 d = ExpVector.EVDIF(c, a); 178 assertTrue("sign(lcm(a,b)-a) >= 0", ExpVector.EVSIGN(d) >= 0); 179 d = ExpVector.EVDIF(c, b); 180 assertTrue("sign(lcm(a,b)-b) >= 0", ExpVector.EVSIGN(d) >= 0); 181 } 182 183 184 /** 185 * Test tdeg. 186 */ 187 public void testTdeg() { 188 a = ExpVector.create(100); 189 assertTrue("tdeg(a) = 0", ExpVector.EVTDEG(a) == 0); 190 191 float q = (float) 0.2; 192 193 a = ExpVector.EVRAND(5, 10, q); 194 b = ExpVector.EVRAND(5, 10, q); 195 196 assertTrue("tdeg(a) >= 0", ExpVector.EVTDEG(a) >= 0); 197 assertTrue("tdeg(b) >= 0", ExpVector.EVTDEG(b) >= 0); 198 199 c = ExpVector.EVSUM(a, b); 200 assertTrue("tdeg(a+b) >= tdeg(a)", ExpVector.EVTDEG(c) >= ExpVector.EVTDEG(a)); 201 assertTrue("tdeg(a+b) >= tdeg(b)", ExpVector.EVTDEG(c) >= ExpVector.EVTDEG(b)); 202 203 c = ExpVector.EVLCM(a, b); 204 assertTrue("tdeg(lcm(a,b)) >= tdeg(a)", ExpVector.EVTDEG(c) >= ExpVector.EVTDEG(a)); 205 assertTrue("tdeg(lcm(a,b)) >= tdeg(b)", ExpVector.EVTDEG(c) >= ExpVector.EVTDEG(b)); 206 } 207 208 209 /** 210 * Test weighted. 211 */ 212 public void testWeightdeg() { 213 a = ExpVector.create(100); 214 assertTrue("tdeg(a) = 0", ExpVector.EVTDEG(a) == 0); 215 assertTrue("wdeg(a) = 0", ExpVector.EVWDEG(null, a) == 0); 216 217 float q = (float) 0.2; 218 219 a = ExpVector.EVRAND(5, 10, q); 220 b = ExpVector.EVRAND(5, 10, q); 221 long[][] w = new long[][] { new long[] { 1l, 1l, 1l, 1l, 1l } }; 222 223 assertTrue("tdeg(a) >= 0", ExpVector.EVTDEG(a) >= 0); 224 assertTrue("tdeg(b) >= 0", ExpVector.EVTDEG(b) >= 0); 225 226 assertTrue("wdeg(a) >= 0", ExpVector.EVWDEG(w, a) >= 0); 227 assertTrue("wdeg(b) >= 0", ExpVector.EVWDEG(w, b) >= 0); 228 229 assertEquals("tdeg(a) == wdeg(a)", ExpVector.EVTDEG(a), ExpVector.EVWDEG(w, a)); 230 assertEquals("tdeg(b) == wdeg(b)", ExpVector.EVTDEG(b), ExpVector.EVWDEG(w, b)); 231 232 c = ExpVector.EVSUM(a, b); 233 assertTrue("wdeg(a+b) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 234 assertTrue("wdeg(a+b) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 235 236 c = ExpVector.EVLCM(a, b); 237 assertTrue("wdeg(lcm(a,b)) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 238 assertTrue("wdeg(lcm(a,b)) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 239 240 241 w = new long[][] { new long[] { 10l, 1l, 3l, 9l, 100l } }; 242 243 assertTrue("tdeg(a) >= 0", ExpVector.EVTDEG(a) >= 0); 244 assertTrue("tdeg(b) >= 0", ExpVector.EVTDEG(b) >= 0); 245 246 assertTrue("wdeg(a) >= 0", ExpVector.EVWDEG(w, a) >= 0); 247 assertTrue("wdeg(b) >= 0", ExpVector.EVWDEG(w, b) >= 0); 248 249 assertTrue("tdeg(a) <= wdeg(a)", ExpVector.EVTDEG(a) <= ExpVector.EVWDEG(w, a)); 250 assertTrue("tdeg(b) <= wdeg(b)", ExpVector.EVTDEG(b) <= ExpVector.EVWDEG(w, b)); 251 252 c = ExpVector.EVSUM(a, b); 253 assertTrue("wdeg(a+b) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 254 assertTrue("wdeg(a+b) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 255 256 c = ExpVector.EVLCM(a, b); 257 assertTrue("wdeg(lcm(a,b)) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 258 assertTrue("wdeg(lcm(a,b)) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 259 260 261 w = new long[][] { new long[] { 10l, 1l, 3l, 9l, 100l }, new long[] { 1l, 1l, 1l, 1l, 1l } }; 262 263 assertTrue("tdeg(a) >= 0", ExpVector.EVTDEG(a) >= 0); 264 assertTrue("tdeg(b) >= 0", ExpVector.EVTDEG(b) >= 0); 265 266 assertTrue("wdeg(a) >= 0", ExpVector.EVWDEG(w, a) >= 0); 267 assertTrue("wdeg(b) >= 0", ExpVector.EVWDEG(w, b) >= 0); 268 269 assertTrue("tdeg(a) <= wdeg(a)", ExpVector.EVTDEG(a) <= ExpVector.EVWDEG(w, a)); 270 assertTrue("tdeg(b) <= wdeg(b)", ExpVector.EVTDEG(b) <= ExpVector.EVWDEG(w, b)); 271 272 c = ExpVector.EVSUM(a, b); 273 assertTrue("wdeg(a+b) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 274 assertTrue("wdeg(a+b) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 275 276 c = ExpVector.EVLCM(a, b); 277 assertTrue("wdeg(lcm(a,b)) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 278 assertTrue("wdeg(lcm(a,b)) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 279 280 } 281 282 283 /** 284 * Test dependency on variables. 285 */ 286 public void testDependency() { 287 int[] exp; 288 int[] dep; 289 290 a = ExpVector.create(10, 5, 2l); 291 exp = new int[] { 5 }; 292 dep = ExpVector.EVDOV(a); 293 assertTrue("[5] = [5]", Arrays.equals(exp, dep)); 294 295 b = ExpVector.create(10, 3, 9l); 296 exp = new int[] { 3 }; 297 dep = ExpVector.EVDOV(b); 298 assertTrue("[3] = [3]", Arrays.equals(exp, dep)); 299 300 c = ExpVector.EVSUM(a, b); 301 exp = new int[] { 3, 5 }; 302 dep = ExpVector.EVDOV(c); 303 assertTrue("[3,5] = [3,5] " + Arrays.toString(exp) + "," + Arrays.toString(dep), 304 Arrays.equals(exp, dep)); 305 306 b = ExpVector.create(10); 307 exp = new int[] {}; 308 dep = ExpVector.EVDOV(b); 309 assertTrue("[] = []", Arrays.equals(exp, dep)); 310 311 b = ExpVector.create(0); 312 exp = new int[] {}; 313 dep = ExpVector.EVDOV(b); 314 assertTrue("[] = []", Arrays.equals(exp, dep)); 315 316 b = ExpVector.create(1, 0, 1l); 317 exp = new int[] { 0 }; 318 dep = ExpVector.EVDOV(b); 319 assertTrue("[0] = [0]", Arrays.equals(exp, dep)); 320 } 321 322 323 /** 324 * Test random exp vector 2. 325 */ 326 public void testRandom2() { 327 float q = (float) 0.2; 328 329 a = ExpVector.EVRAND(5, 10, q); 330 b = ExpVector.create("" + a); 331 332 assertEquals("a == b", true, a.equals(b)); 333 334 c = b.subtract(a); 335 336 assertTrue("a-b = 0", c.isZERO()); 337 } 338 339 340 /** 341 * Test addition. 342 */ 343 public void testAddition2() { 344 float q = (float) 0.2; 345 346 a = ExpVector.EVRAND(5, 10, q); 347 348 b = a.sum(a); 349 c = b.subtract(a); 350 351 assertEquals("a+a-a = a", c, a); 352 assertTrue("a+a-a = a", c.equals(a)); 353 354 boolean t; 355 t = b.multipleOf(a); 356 assertTrue("a | a+a", t); 357 358 a = ExpVector.EVRAND(5, 10, q); 359 b = ExpVector.EVRAND(5, 10, q); 360 361 c = a.sum(b); 362 d = b.sum(a); 363 assertTrue("a+b = b+a", c.equals(d)); 364 } 365 366 367 /** 368 * Test lcm. 369 */ 370 public void testLcm2() { 371 float q = (float) 0.2; 372 373 a = ExpVector.EVRAND(5, 10, q); 374 b = ExpVector.EVRAND(5, 10, q); 375 c = a.lcm(b); 376 d = b.lcm(a); 377 378 assertTrue("lcm(a,b) = lcm(b,a)", c.equals(d)); 379 380 assertTrue("a | lcm(a,b)", c.multipleOf(a)); 381 assertTrue("b | lcm(a,b)", c.multipleOf(b)); 382 383 d = c.subtract(a); 384 assertTrue("sign(lcm(a,b)-a) >= 0", d.signum() >= 0); 385 d = c.subtract(b); 386 assertTrue("sign(lcm(a,b)-b) >= 0", d.signum() >= 0); 387 } 388 389 390 /** 391 * Test tdeg. 392 */ 393 public void testTdeg2() { 394 a = ExpVector.create(100); 395 assertTrue("tdeg(a) = 0", ExpVector.EVTDEG(a) == 0); 396 397 float q = (float) 0.2; 398 399 a = ExpVector.EVRAND(5, 10, q); 400 b = ExpVector.EVRAND(5, 10, q); 401 402 assertTrue("tdeg(a) >= 0", ExpVector.EVTDEG(a) >= 0); 403 assertTrue("tdeg(b) >= 0", ExpVector.EVTDEG(b) >= 0); 404 405 c = a.sum(b); 406 assertTrue("tdeg(a+b) >= tdeg(a)", ExpVector.EVTDEG(c) >= ExpVector.EVTDEG(a)); 407 assertTrue("tdeg(a+b) >= tdeg(b)", ExpVector.EVTDEG(c) >= ExpVector.EVTDEG(b)); 408 409 c = a.lcm(b); 410 assertTrue("tdeg(lcm(a,b)) >= tdeg(a)", ExpVector.EVTDEG(c) >= ExpVector.EVTDEG(a)); 411 assertTrue("tdeg(lcm(a,b)) >= tdeg(b)", ExpVector.EVTDEG(c) >= ExpVector.EVTDEG(b)); 412 } 413 414 415 /** 416 * Test weighted. 417 */ 418 public void testWeightdeg2() { 419 a = ExpVector.create(100); 420 assertTrue("tdeg(a) = 0", ExpVector.EVTDEG(a) == 0); 421 assertTrue("wdeg(a) = 0", ExpVector.EVWDEG(null, a) == 0); 422 423 float q = (float) 0.2; 424 425 a = ExpVector.EVRAND(5, 10, q); 426 b = ExpVector.EVRAND(5, 10, q); 427 long[][] w = new long[][] { new long[] { 1l, 1l, 1l, 1l, 1l } }; 428 429 assertTrue("tdeg(a) >= 0", ExpVector.EVTDEG(a) >= 0); 430 assertTrue("tdeg(b) >= 0", ExpVector.EVTDEG(b) >= 0); 431 432 assertTrue("wdeg(a) >= 0", ExpVector.EVWDEG(w, a) >= 0); 433 assertTrue("wdeg(b) >= 0", ExpVector.EVWDEG(w, b) >= 0); 434 435 assertEquals("tdeg(a) == wdeg(a)", ExpVector.EVTDEG(a), ExpVector.EVWDEG(w, a)); 436 assertEquals("tdeg(b) == wdeg(b)", ExpVector.EVTDEG(b), ExpVector.EVWDEG(w, b)); 437 438 c = a.sum(b); 439 assertTrue("wdeg(a+b) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 440 assertTrue("wdeg(a+b) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 441 442 c = a.lcm(b); 443 assertTrue("wdeg(lcm(a,b)) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 444 assertTrue("wdeg(lcm(a,b)) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 445 446 447 w = new long[][] { new long[] { 10l, 1l, 3l, 9l, 100l } }; 448 449 assertTrue("tdeg(a) >= 0", ExpVector.EVTDEG(a) >= 0); 450 assertTrue("tdeg(b) >= 0", ExpVector.EVTDEG(b) >= 0); 451 452 assertTrue("wdeg(a) >= 0", ExpVector.EVWDEG(w, a) >= 0); 453 assertTrue("wdeg(b) >= 0", ExpVector.EVWDEG(w, b) >= 0); 454 455 assertTrue("tdeg(a) <= wdeg(a)", ExpVector.EVTDEG(a) <= ExpVector.EVWDEG(w, a)); 456 assertTrue("tdeg(b) <= wdeg(b)", ExpVector.EVTDEG(b) <= ExpVector.EVWDEG(w, b)); 457 458 c = a.sum(b); 459 assertTrue("wdeg(a+b) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 460 assertTrue("wdeg(a+b) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 461 462 c = a.lcm(b); 463 assertTrue("wdeg(lcm(a,b)) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 464 assertTrue("wdeg(lcm(a,b)) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 465 466 467 w = new long[][] { new long[] { 10l, 1l, 3l, 9l, 100l }, new long[] { 1l, 1l, 1l, 1l, 1l } }; 468 469 assertTrue("tdeg(a) >= 0", ExpVector.EVTDEG(a) >= 0); 470 assertTrue("tdeg(b) >= 0", ExpVector.EVTDEG(b) >= 0); 471 472 assertTrue("wdeg(a) >= 0", ExpVector.EVWDEG(w, a) >= 0); 473 assertTrue("wdeg(b) >= 0", ExpVector.EVWDEG(w, b) >= 0); 474 475 assertTrue("tdeg(a) <= wdeg(a)", ExpVector.EVTDEG(a) <= ExpVector.EVWDEG(w, a)); 476 assertTrue("tdeg(b) <= wdeg(b)", ExpVector.EVTDEG(b) <= ExpVector.EVWDEG(w, b)); 477 478 c = a.sum(b); 479 assertTrue("wdeg(a+b) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 480 assertTrue("wdeg(a+b) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 481 482 c = a.lcm(b); 483 assertTrue("wdeg(lcm(a,b)) >= wdeg(a)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, a)); 484 assertTrue("wdeg(lcm(a,b)) >= wdeg(b)", ExpVector.EVWDEG(w, c) >= ExpVector.EVWDEG(w, b)); 485 486 } 487 488 489 /** 490 * Test dependency on variables. 491 */ 492 public void testDependency2() { 493 int[] exp; 494 int[] dep; 495 496 a = ExpVector.create(10, 5, 2l); 497 exp = new int[] { 5 }; 498 dep = a.dependencyOnVariables(); 499 assertTrue("[5] = [5]", Arrays.equals(exp, dep)); 500 501 b = ExpVector.create(10, 3, 9l); 502 exp = new int[] { 3 }; 503 dep = b.dependencyOnVariables(); 504 assertTrue("[3] = [3]", Arrays.equals(exp, dep)); 505 506 c = a.sum(b); 507 exp = new int[] { 3, 5 }; 508 dep = c.dependencyOnVariables(); 509 assertTrue("[3,5] = [3,5] " + Arrays.toString(exp) + "," + Arrays.toString(dep), 510 Arrays.equals(exp, dep)); 511 512 b = ExpVector.create(10); 513 exp = new int[] {}; 514 dep = b.dependencyOnVariables(); 515 assertTrue("[] = []", Arrays.equals(exp, dep)); 516 517 b = ExpVector.create(0); 518 exp = new int[] {}; 519 dep = b.dependencyOnVariables(); 520 assertTrue("[] = []", Arrays.equals(exp, dep)); 521 522 b = ExpVector.create(1, 0, 1l); 523 exp = new int[] { 0 }; 524 dep = b.dependencyOnVariables(); 525 assertTrue("[0] = [0]", Arrays.equals(exp, dep)); 526 } 527 528 529 /** 530 * Test evaluation. 531 */ 532 public void testEvaluation() { 533 float q = (float) 0.2; 534 int rl = 5; 535 536 a = ExpVector.EVRAND(rl, 10, q); 537 b = ExpVector.EVRAND(rl, 10, q); 538 BigInteger fv = new BigInteger(0); 539 List<BigInteger> v = new ArrayList<BigInteger>(a.length()); 540 for (int i = 0; i < a.length(); i++) { 541 v.add(fv.random(4)); 542 } 543 544 BigInteger av = a.evaluate(fv, v); 545 BigInteger bv = b.evaluate(fv, v); 546 547 c = a.sum(b); 548 BigInteger cv = c.evaluate(fv, v); 549 BigInteger dv = av.multiply(bv); 550 551 assertEquals("a(v)*b(v) = (a+b)(v) ", cv, dv); 552 553 c = ExpVector.create(rl); 554 cv = c.evaluate(fv, v); 555 dv = fv.getONE(); 556 assertEquals("0(v) = 1 ", cv, dv); 557 558 v.clear(); 559 for (int i = 0; i < a.length(); i++) { 560 v.add(fv.getZERO()); 561 } 562 cv = c.evaluate(fv, v); 563 dv = fv.getONE(); 564 assertEquals("0(0) = 1 ", cv, dv); 565 566 av = a.evaluate(fv, v); 567 if (a.isZERO()) { 568 dv = fv.getONE(); 569 assertEquals("0(0) = 1 ", av, dv); 570 } else { 571 dv = fv.getZERO(); 572 assertEquals("a(0) = 0 ", av, dv); 573 } 574 } 575 576}