| 630 | } |
| 631 | |
| 632 | void |
| 633 | Solver::reconstruct_gradient() |
| 634 | { |
| 635 | // reconstruct inactive elements of G from G_bar and free variables |
| 636 | |
| 637 | if (active_size == l) |
| 638 | return; |
| 639 | |
| 640 | int nr_free = 0; |
| 641 | |
| 642 | for (int j = active_size; j < l; j++) |
| 643 | G[j] = G_bar[j] + p[j]; |
| 644 | |
| 645 | for (int j = 0; j < active_size; j++) |
| 646 | if (is_free(j)) |
| 647 | nr_free++; |
| 648 | |
| 649 | if (2 * nr_free < active_size) |
| 650 | info("\nWARNING: using -h 0 may be faster\n"); |
| 651 | |
| 652 | if (nr_free * l > 2 * active_size * (l - active_size)) { |
| 653 | for (int i = active_size; i < l; i++) { |
| 654 | const Qfloat* Q_i = Q->get_Q(i, active_size); |
| 655 | |
| 656 | for (int j = 0; j < active_size; j++) |
| 657 | if (is_free(j)) |
| 658 | G[i] += alpha[j] * Q_i[j]; |
| 659 | } |
| 660 | } |
| 661 | else { |
| 662 | for (int i = 0; i < active_size; i++) |
| 663 | if (is_free(i)) { |
| 664 | const Qfloat* Q_i = Q->get_Q(i, l); |
| 665 | double alpha_i = alpha[i]; |
| 666 | |
| 667 | for (int j = active_size; j < l; j++) |
| 668 | G[j] += alpha_i * Q_i[j]; |
| 669 | } |
| 670 | } |
| 671 | } |
| 672 | |
| 673 | void |
| 674 | Solver::Solve(int l, |