Current task: —

E-022b-valley-analysis.py

Experiments: E-022b · script updated 08-19-2026

E-022b-valley.csv — 87.2 KB, updated 08-19-2026

← prev page 6 of 10 · 500/page · 4600 rows next →
# azlogK
2502 8 47.000 2.754859
2503 8 47.050 2.754308
2504 8 47.100 2.758218
2505 8 47.150 2.764593
2506 8 47.200 2.769250
2507 8 47.250 2.767877
2508 8 47.300 2.758559
2509 8 47.350 2.743615
2510 8 47.400 2.729629
2511 8 47.450 2.724756
2512 8 47.500 2.733518
2513 8 47.550 2.751805
2514 8 47.600 2.765769
2515 8 47.650 2.755006
2516 8 47.700 2.696550
2517 8 47.750 2.566361
2518 8 47.800 2.337328
2519 8 47.850 1.973757
2520 8 47.900 1.423272
2521 8 47.950 0.635021
2522 8 48.000 -0.051971
2523 8 48.050 0.452013
2524 8 48.100 1.280730
2525 8 48.150 1.877975
2526 8 48.200 2.274645
2527 8 48.250 2.526980
2528 8 48.300 2.673707
2529 8 48.350 2.743669
2530 8 48.400 2.761984
2531 8 48.450 2.752409
2532 8 48.500 2.735935
2533 8 48.550 2.726738
2534 8 48.600 2.729075
2535 8 48.650 2.738771
2536 8 48.700 2.748650
2537 8 48.750 2.753830
2538 8 48.800 2.753929
2539 8 48.850 2.751974
2540 8 48.900 2.751359
2541 8 48.950 2.752955
2542 8 49.000 2.754367
2543 8 49.050 2.751879
2544 8 49.100 2.743722
2545 8 49.150 2.732472
2546 8 49.200 2.724756
2547 8 49.250 2.727419
2548 8 49.300 2.741529
2549 8 49.350 2.758236
2550 8 49.400 2.759640
2551 8 49.450 2.722999
2552 8 49.500 2.623991
2553 8 49.550 2.436504
2554 8 49.600 2.128617
2555 8 49.650 1.654995
2556 8 49.700 0.955312
2557 8 49.750 0.113925
2558 8 49.800 0.146671
2559 8 49.850 0.992793
2560 8 49.900 1.679625
2561 8 49.950 2.143923
2562 8 50.000 2.446158
2563 8 50.050 2.630728
2564 8 50.100 2.728686
2565 8 50.150 2.765146
2566 8 50.200 2.763321
2567 8 50.250 2.745158
2568 8 50.300 2.728782
2569 8 50.350 2.724476
2570 8 50.400 2.732885
2571 8 50.450 2.747710
2572 8 50.500 2.761014
2573 8 50.550 2.767559
2574 8 50.600 2.766488
2575 8 50.650 2.760668
2576 8 50.700 2.754645
2577 8 50.750 2.752207
2578 8 50.800 2.754629
2579 8 50.850 2.760410
2580 8 50.900 2.766470
2581 8 50.950 2.769925
2582 8 51.000 2.769455
2583 8 51.050 2.765742
2584 8 51.100 2.760960
2585 8 51.150 2.757624
2586 8 51.200 2.757326
2587 8 51.250 2.759997
2588 8 51.300 2.764046
2589 8 51.350 2.767271
2590 8 51.400 2.768022
2591 8 51.450 2.766028
2592 8 51.500 2.762521
2593 8 51.550 2.759598
2594 8 51.600 2.759085
2595 8 51.650 2.761459
2596 8 51.700 2.765459
2597 8 51.750 2.768688
2598 8 51.800 2.768902
2599 8 51.850 2.765323
2600 8 51.900 2.759299
2601 8 51.950 2.753869
2602 8 52.000 2.752243
2603 8 52.050 2.755806
2604 8 52.100 2.762851
2605 8 52.150 2.769021
2606 8 52.200 2.769393
2607 8 52.250 2.761205
2608 8 52.300 2.745976
2609 8 52.350 2.729962
2610 8 52.400 2.721945
2611 8 52.450 2.728187
2612 8 52.500 2.746848
2613 8 52.550 2.765873
2614 8 52.600 2.765719
2615 8 52.650 2.723777
2616 8 52.700 2.616666
2617 8 52.750 2.419061
2618 8 52.800 2.099133
2619 8 52.850 1.610788
2620 8 52.900 0.894528
2621 8 52.950 0.069342
2622 8 53.000 0.197418
2623 8 53.050 1.047938
2624 8 53.100 1.719214
2625 8 53.150 2.172258
2626 8 53.200 2.466538
2627 8 53.250 2.644807
2628 8 53.300 2.737227
2629 8 53.350 2.768694
2630 8 53.400 2.762786
2631 8 53.450 2.742189
2632 8 53.500 2.725582
2633 8 53.550 2.722965
2634 8 53.600 2.733779
2635 8 53.650 2.750311
2636 8 53.700 2.763831
2637 8 53.750 2.769260
2638 8 53.800 2.766652
2639 8 53.850 2.760010
2640 8 53.900 2.754569
2641 8 53.950 2.753851
2642 8 54.000 2.757987
2643 8 54.050 2.764176
2644 8 54.100 2.768741
2645 8 54.150 2.769347
2646 8 54.200 2.766140
2647 8 54.250 2.761437
2648 8 54.300 2.758258
2649 8 54.350 2.758541
2650 8 54.400 2.762057
2651 8 54.450 2.766669
2652 8 54.500 2.769711
2653 8 54.550 2.769545
2654 8 54.600 2.766448
2655 8 54.650 2.762380
2656 8 54.700 2.759815
2657 8 54.750 2.760268
2658 8 54.800 2.763383
2659 8 54.850 2.767187
2660 8 54.900 2.769314
2661 8 54.950 2.768440
2662 8 55.000 2.765077
2663 8 55.050 2.761304
2664 8 55.100 2.759538
2665 8 55.150 2.760991
2666 8 55.200 2.764795
2667 8 55.250 2.768417
2668 8 55.300 2.769166
2669 8 55.350 2.765889
2670 8 55.400 2.759880
2671 8 55.450 2.754403
2672 8 55.500 2.752876
2673 8 55.550 2.756555
2674 8 55.600 2.763245
2675 8 55.650 2.768103
2676 8 55.700 2.766239
2677 8 55.750 2.755733
2678 8 55.800 2.739615
2679 8 55.850 2.725569
2680 8 55.900 2.722431
2681 8 55.950 2.734130
2682 8 56.000 2.754649
2683 8 56.050 2.767900
2684 8 56.100 2.751935
2685 8 56.150 2.683088
2686 8 56.200 2.536923
2687 8 56.250 2.285491
2688 8 56.300 1.891084
2689 8 56.350 1.298583
2690 8 56.400 0.474714
2691 8 56.450 -0.055971
2692 8 56.500 0.607176
2693 8 56.550 1.399477
2694 8 56.600 1.955899
2695 8 56.650 2.324624
2696 8 56.700 2.558211
2697 8 56.750 2.692453
2698 8 56.800 2.754306
2699 8 56.850 2.767453
2700 8 56.900 2.754464
2701 8 56.950 2.735604
2702 8 57.000 2.725122
2703 8 57.050 2.728007
2704 8 57.100 2.740633
2705 8 57.150 2.755292
2706 8 57.200 2.765270
2707 8 57.250 2.767698
2708 8 57.300 2.763785
2709 8 57.350 2.757309
2710 8 57.400 2.752371
2711 8 57.450 2.751448
2712 8 57.500 2.754560
2713 8 57.550 2.759798
2714 8 57.600 2.764651
2715 8 57.650 2.767258
2716 8 57.700 2.767045
2717 8 57.750 2.764665
2718 8 57.800 2.761481
2719 8 57.850 2.758926
2720 8 57.900 2.757963
2721 8 57.950 2.758802
2722 8 58.000 2.760880
2723 8 58.050 2.763077
2724 8 58.100 2.764119
2725 8 58.150 2.763084
2726 8 58.200 2.759906
2727 8 58.250 2.755630
2728 8 58.300 2.752204
2729 8 58.350 2.751671
2730 8 58.400 2.754985
2731 8 58.450 2.761061
2732 8 58.500 2.766775
2733 8 58.550 2.768138
2734 8 58.600 2.762273
2735 8 58.650 2.749344
2736 8 58.700 2.733579
2737 8 58.750 2.722371
2738 8 58.800 2.722833
2739 8 58.850 2.736708
2740 8 58.900 2.756751
2741 8 58.950 2.767254
2742 8 59.000 2.747669
2743 8 59.050 2.675812
2744 8 59.100 2.528320
2745 8 59.150 2.277909
2746 8 59.200 1.887366
2747 8 59.250 1.302099
2748 8 59.300 0.486897
2749 8 59.350 -0.058491
2750 8 59.400 0.589399
2751 8 59.450 1.388766
2752 8 59.500 1.953083
2753 8 59.550 2.327429
2754 8 59.600 2.563774
2755 8 59.650 2.697467
2756 8 59.700 2.755379
2757 8 59.750 2.762061
2758 8 59.800 2.742423
2759 8 59.850 2.720145
2760 8 59.900 2.711953
2761 8 59.950 2.721935
2762 10 14.000 2.303007
2763 10 14.050 1.626646
2764 10 14.100 0.533091
2765 10 14.150 0.095016
2766 10 14.200 1.253751
2767 10 14.250 2.081520
2768 10 14.300 2.569397
2769 10 14.350 2.840043
2770 10 14.400 2.964807
2771 10 14.450 2.995210
2772 10 14.500 2.977926
2773 10 14.550 2.954507
2774 10 14.600 2.950011
2775 10 14.650 2.965056
2776 10 14.700 2.984553
2777 10 14.750 2.994656
2778 10 14.800 2.992320
2779 10 14.850 2.984206
2780 10 14.900 2.979411
2781 10 14.950 2.982021
2782 10 15.000 2.989008
2783 10 15.050 2.994313
2784 10 15.100 2.994411
2785 10 15.150 2.990618
2786 10 15.200 2.987161
2787 10 15.250 2.987262
2788 10 15.300 2.990612
2789 10 15.350 2.994199
2790 10 15.400 2.995255
2791 10 15.450 2.993512
2792 10 15.500 2.991047
2793 10 15.550 2.990223
2794 10 15.600 2.991640
2795 10 15.650 2.993862
2796 10 15.700 2.994932
2797 10 15.750 2.994137
2798 10 15.800 2.992483
2799 10 15.850 2.991636
2800 10 15.900 2.992388
2801 10 15.950 2.994029
2802 10 16.000 2.995109
2803 10 16.050 2.994781
2804 10 16.100 2.993496
2805 10 16.150 2.992508
2806 10 16.200 2.992713
2807 10 16.250 2.993882
2808 10 16.300 2.994947
2809 10 16.350 2.995009
2810 10 16.400 2.994119
2811 10 16.450 2.993168
2812 10 16.500 2.993039
2813 10 16.550 2.993823
2814 10 16.600 2.994785
2815 10 16.650 2.995074
2816 10 16.700 2.994496
2817 10 16.750 2.993640
2818 10 16.800 2.993310
2819 10 16.850 2.993785
2820 10 16.900 2.994592
2821 10 16.950 2.994980
2822 10 17.000 2.994622
2823 10 17.050 2.993900
2824 10 17.100 2.993530
2825 10 17.150 2.993883
2826 10 17.200 2.994646
2827 10 17.250 2.995118
2828 10 17.300 2.994863
2829 10 17.350 2.994109
2830 10 17.400 2.993537
2831 10 17.450 2.993654
2832 10 17.500 2.994326
2833 10 17.550 2.994913
2834 10 17.600 2.994867
2835 10 17.650 2.994235
2836 10 17.700 2.993619
2837 10 17.750 2.993616
2838 10 17.800 2.994257
2839 10 17.850 2.994972
2840 10 17.900 2.995103
2841 10 17.950 2.994515
2842 10 18.000 2.993722
2843 10 18.050 2.993425
2844 10 18.100 2.993865
2845 10 18.150 2.994602
2846 10 18.200 2.994921
2847 10 18.250 2.994501
2848 10 18.300 2.993725
2849 10 18.350 2.993330
2850 10 18.400 2.993712
2851 10 18.450 2.994524
2852 10 18.500 2.994974
2853 10 18.550 2.994562
2854 10 18.600 2.993588
2855 10 18.650 2.992921
2856 10 18.700 2.993218
2857 10 18.750 2.994272
2858 10 18.800 2.995129
2859 10 18.850 2.994928
2860 10 18.900 2.993705
2861 10 18.950 2.992440
2862 10 19.000 2.992223
2863 10 19.050 2.993255
2864 10 19.100 2.994600
2865 10 19.150 2.994981
2866 10 19.200 2.993944
2867 10 19.250 2.992327
2868 10 19.300 2.991572
2869 10 19.350 2.992394
2870 10 19.400 2.994033
2871 10 19.450 2.994855
2872 10 19.500 2.993841
2873 10 19.550 2.991640
2874 10 19.600 2.990143
2875 10 19.650 2.990795
2876 10 19.700 2.993095
2877 10 19.750 2.994799
2878 10 19.800 2.993853
2879 10 19.850 2.990424
2880 10 19.900 2.987139
2881 10 19.950 2.986986
2882 10 20.000 2.990418
2883 10 20.050 2.994386
2884 10 20.100 2.994635
2885 10 20.150 2.989551
2886 10 20.200 2.982295
2887 10 20.250 2.978898
2888 10 20.300 2.982924
2889 10 20.350 2.991063
2890 10 20.400 2.994518
2891 10 20.450 2.986007
2892 10 20.500 2.967231
2893 10 20.550 2.950903
2894 10 20.600 2.952639
2895 10 20.650 2.974494
2896 10 20.700 2.994479
2897 10 20.750 2.972682
2898 10 20.800 2.863040
2899 10 20.850 2.615356
2900 10 20.900 2.162543
2901 10 20.950 1.390644
2902 10 21.000 0.229371
2903 10 21.050 0.366014
2904 10 21.100 1.504526
2905 10 21.150 2.230747
2906 10 21.200 2.654618
2907 10 21.250 2.882685
2908 10 21.300 2.978897
2909 10 21.350 2.992848
2910 10 21.400 2.970612
2911 10 21.450 2.950859
2912 10 21.500 2.952461
2913 10 21.550 2.970343
2914 10 21.600 2.988145
2915 10 21.650 2.994482
2916 10 21.700 2.989508
2917 10 21.750 2.981524
2918 10 21.800 2.978874
2919 10 21.850 2.983447
2920 10 21.900 2.990608
2921 10 21.950 2.994472
2922 10 22.000 2.992974
2923 10 22.050 2.988781
2924 10 22.100 2.986287
2925 10 22.150 2.987663
2926 10 22.200 2.991367
2927 10 22.250 2.994082
2928 10 22.300 2.993857
2929 10 22.350 2.991568
2930 10 22.400 2.989762
2931 10 22.450 2.990191
2932 10 22.500 2.992333
2933 10 22.550 2.994130
2934 10 22.600 2.994034
2935 10 22.650 2.992360
2936 10 22.700 2.990832
2937 10 22.750 2.990878
2938 10 22.800 2.992331
2939 10 22.850 2.993720
2940 10 22.900 2.993773
2941 10 22.950 2.992618
2942 10 23.000 2.991573
2943 10 23.050 2.991790
2944 10 23.100 2.993081
2945 10 23.150 2.994103
2946 10 23.200 2.993714
2947 10 23.250 2.992151
2948 10 23.300 2.990867
2949 10 23.350 2.991131
2950 10 23.400 2.992706
2951 10 23.450 2.993977
2952 10 23.500 2.993485
2953 10 23.550 2.991427
2954 10 23.600 2.989643
2955 10 23.650 2.989927
2956 10 23.700 2.992165
2957 10 23.750 2.994188
2958 10 23.800 2.993694
2959 10 23.850 2.990552
2960 10 23.900 2.987280
2961 10 23.950 2.986940
2962 10 24.000 2.990064
2963 10 24.050 2.993608
2964 10 24.100 2.993382
2965 10 24.150 2.988059
2966 10 24.200 2.981189
2967 10 24.250 2.978841
2968 10 24.300 2.983897
2969 10 24.350 2.991994
2970 10 24.400 2.993891
2971 10 24.450 2.983191
2972 10 24.500 2.963588
2973 10 24.550 2.949471
2974 10 24.600 2.955505
2975 10 24.650 2.979431
2976 10 24.700 2.994375
2977 10 24.750 2.957812
2978 10 24.800 2.822602
2979 10 24.850 2.536170
2980 10 24.900 2.024065
2981 10 24.950 1.158230
2982 10 25.000 0.026321
2983 10 25.050 0.643150
2984 10 25.100 1.700211
2985 10 25.150 2.345392
2986 10 25.200 2.718194
2987 10 25.250 2.912412
2988 10 25.300 2.986890
2989 10 25.350 2.989659
2990 10 25.400 2.965393
2991 10 25.450 2.949160
2992 10 25.500 2.954681
2993 10 25.550 2.973663
2994 10 25.600 2.990049
2995 10 25.650 2.994469
2996 10 25.700 2.988614
2997 10 25.750 2.980954
2998 10 25.800 2.979004
2999 10 25.850 2.983867
3000 10 25.900 2.990846
3001 10 25.950 2.994503

E-022b-valley.json — 3.5 KB, updated 08-19-2026

JSON sidecar (click to expand)
{
  "experiment": "E-022b",
  "task": "2.10 analysis: K-diagonal valleys + mass concentration",
  "script": "research/numerics/scripts/E-022b-valley-analysis.py",
  "checks": {
    "V1_valleys_at_gamma": true,
    "V2_mass_concentrated": true,
    "V4_fit_quality": true
  },
  "key_values": {
    "4": {
      "valley_depth": 2.1593140478568413,
      "logK_at_gamma": -0.106956845297883,
      "logK_at_midpoints": 2.0523572025589583,
      "mass_frac_pm0.1": 0.6338714893637662,
      "uniform_expectation": 0.09000000000000001,
      "mass_ratio_vs_uniform": 7.043016548486291,
      "within_bin_meanlogw": {
        "z10-60_d0.0-0.1": 0.05321233524569066,
        "z10-60_d0.3-0.7": -1.7997896503200193,
        "z120-200_d0.0-0.1": 0.10247759965464488,
        "z120-200_d0.3-0.7": -1.7570525979064509
      },
      "elapsed_s": 2.9
    },
    "6": {
      "valley_depth": 2.5087271936533595,
      "logK_at_gamma": -0.04029578260580941,
      "logK_at_midpoints": 2.46843141104755,
      "mass_frac_pm0.1": 0.6986826134175042,
      "uniform_expectation": 0.09000000000000001,
      "mass_ratio_vs_uniform": 7.7631401490833785,
      "within_bin_meanlogw": {
        "z10-60_d0.0-0.1": -0.10145611105454076,
        "z10-60_d0.3-0.7": -2.4097253102207548,
        "z120-200_d0.0-0.1": 0.029192545882919238,
        "z120-200_d0.3-0.7": -2.314439077156247
      },
      "elapsed_s": 5.1
    },
    "8": {
      "valley_depth": 2.7352201581877043,
      "logK_at_gamma": 0.030554703235580436,
      "logK_at_midpoints": 2.7657748614232847,
      "mass_frac_pm0.1": 0.7251109123178877,
      "uniform_expectation": 0.09000000000000001,
      "mass_ratio_vs_uniform": 8.056787914643197,
      "within_bin_meanlogw": {
        "z10-60_d0.0-0.1": -0.1389960979715335,
        "z10-60_d0.3-0.7": -2.7392603482112916,
        "z120-200_d0.0-0.1": -0.20043183472111312,
        "z120-200_d0.3-0.7": -2.6451890375288283
      },
      "elapsed_s": 7.9
    },
    "10": {
      "valley_depth": 2.8706885758089333,
      "logK_at_gamma": 0.11948603922925684,
      "logK_at_midpoints": 2.9901746150381903,
      "mass_frac_pm0.1": 0.7251715332604941,
      "uniform_expectation": 0.09000000000000001,
      "mass_ratio_vs_uniform": 8.057461480672156,
      "within_bin_meanlogw": {
        "z10-60_d0.0-0.1": -0.07371951844373904,
        "z10-60_d0.3-0.7": -2.974563705268562,
        "z120-200_d0.0-0.1": -0.2233480705431757,
        "z120-200_d0.3-0.7": -2.8788847145178686
      },
      "elapsed_s": 11.4
    },
    "12": {
      "valley_depth": 2.9442229398281423,
      "logK_at_gamma": 0.22834844487190686,
      "logK_at_midpoints": 3.172571384700049,
      "mass_frac_pm0.1": 0.7241062961289328,
      "uniform_expectation": 0.09000000000000001,
      "mass_ratio_vs_uniform": 8.045625512543698,
      "within_bin_meanlogw": {
        "z10-60_d0.0-0.1": -0.1831905054381875,
        "z10-60_d0.3-0.7": -3.1605455546413452,
        "z120-200_d0.0-0.1": -0.35321115246295404,
        "z120-200_d0.3-0.7": -3.0663074224107776
      },
      "elapsed_s": 15.5
    },
    "V4_saturation_fit": {
      "Delta_inf": 3.3338697242432738,
      "c": 4.760242352939846,
      "max_resid": 0.03176880509994007
    },
    "valley_depths": {
      "4.0": 2.1593140478568413,
      "6.0": 2.5087271936533595,
      "8.0": 2.7352201581877043,
      "10.0": 2.8706885758089333,
      "12.0": 2.9442229398281423
    }
  },
  "elapsed_seconds": 59.7,
  "timestamp_utc": "2026-08-19T17:37:47.138364+00:00"
}

Source code

Python script (click to expand)
"""E-022b — task 2.10 analysis stage: reproducing-kernel valley structure
and gamma-mass concentration (post-hoc analysis of E-022).

E-022 found the coarse weak metric flat (O3) but a persistent mass
elevation near the true zeros. This script resolves the mechanism:

  K_a(z,z) := Re(b_z^H v), v the bordered (L^2_0) Galerkin solution of
  T_a v = e^{-izx} — the diagonal of the model-space reproducing kernel.

Measurements (a in {4,6,8,10,12}, theta=pi):
  V1. valley depth: Delta(a) = mean log K at gamma-gap midpoints minus
      mean log K at gammas, z-grid step 0.05 in [14,60).
  V2. mass concentration: fraction of the E-022 spectral mass within
      +/-0.1 of a true zero (vs uniform-lattice expectation).
  V3. artifact control: mean log w vs distance-to-nearest-gamma WITHIN
      z-bins (controls the gamma-density/weight-trend confound that
      naive O5 fails — shifted-gamma null test showed the raw O5
      elevation is mostly distributional).
  V4. saturation model: Delta(a) ~ Delta_inf - c/a fit.

Outputs: research/numerics/data/E-022b-valley.csv (+ .json)
"""
import importlib.util
import json
import sys
import time
from datetime import datetime, timezone
from pathlib import Path

import mpmath as mp
import numpy as np
import scipy.linalg

REPO = Path(__file__).resolve().parents[3]
DATA = REPO / "research" / "numerics" / "data"
CSV = DATA / "E-022b-valley.csv"
JSON = DATA / "E-022b-valley.json"

spec = importlib.util.spec_from_file_location(
    "E16", Path(__file__).with_name("E-016-herglotz-fine-structure.py"))
E16 = importlib.util.module_from_spec(spec)
spec.loader.exec_module(E16)                     # runs the e^20 sieve
sys.path.insert(0, str(Path(__file__).parent))
from prime_backend_v2 import PrimeBackendV2       # noqa: E402

H = E16.H_MAIN
LAM = E16.LAM_SHIFT
A_LIST = (4.0, 6.0, 8.0, 10.0, 12.0)
XN = E16.XN


def collect_t_points(a, h):
    n_elem = int(round(2 * a / h))
    pts = []

    def add_quad(lo, hi, peak):
        n_lo = int(np.ceil(np.exp(lo)))
        n_hi = int(np.floor(np.exp(hi)))
        if n_hi - n_lo > 64:
            for aa, bb in ((lo, peak), (peak, hi)):
                if bb - aa > 0:
                    mid, half = 0.5 * (aa + bb), 0.5 * (bb - aa)
                    pts.extend(mid + half * XN)
            return
        segs = sorted({lo, peak, hi} |
                      {float(np.log(n))
                       for n in range(max(n_lo, 2), n_hi + 1)
                       if lo < np.log(n) < hi})
        for p0, p1 in zip(segs, segs[1:]):
            if p1 - p0 > 0:
                mid, half = 0.5 * (p0 + p1), 0.5 * (p1 - p0)
                pts.extend(mid + half * XN)

    for k in range(n_elem):
        if k == 0:
            add_quad(0.0, h, 0.0)
        else:
            add_quad((k - 1) * h, (k + 1) * h, k * h)
    return np.array(pts)


def make_K1(a):
    x, h, Q, M, _b = E16.build(a, H)
    n = Q.shape[0]
    mc = np.zeros(n)
    mc[0] = 2 * h / 3
    mc[1] = h / 6
    tc = Q[:, 0] - LAM * mc
    u1 = scipy.linalg.solve_toeplitz((tc, tc), np.ones(n))
    s1 = u1.sum()

    def K1(z):
        bz = E16.hat_FT(np.array([z]), h)[0] * np.exp(-1j * z * x)
        u0 = scipy.linalg.solve_toeplitz((tc, tc), bz)
        v = u0 - (u0.sum() / s1) * u1
        return float(np.real(np.conj(bz) @ v))

    return K1


def main() -> int:
    if JSON.exists() and "--force" not in sys.argv:
        print(f"cached: {JSON} (use --force to recompute)")
        return 0
    t0 = time.time()

    tq = np.concatenate([collect_t_points(a, H) for a in A_LIST])
    be = PrimeBackendV2(tq)
    be.load_cache(DATA / "E-022-backend-cache.npz")
    E16._BUILD.clear()
    E16.prime_sum_vec = be.prime_sum

    mp.mp.dps = 30
    gam_all = np.array([float(mp.zetazero(k).imag)
                        for k in range(1, 201)])
    gam = gam_all[gam_all <= 280]

    # E-022 weights
    import csv as csvmod
    data = {}
    with open(DATA / "E-022-spectral-measure.csv") as f:
        for r in csvmod.DictReader(f):
            data.setdefault(float(r["a"]), []).append(
                (float(r["z_k"]), float(r["w_k"])))

    zgrid = np.arange(14.0, 60.0, 0.05)
    gsel = gam_all[(gam_all >= 14) & (gam_all < 60)]
    mids = (gsel[:-1] + gsel[1:]) / 2
    idxg = np.round((gsel - 14) / 0.05).astype(int)
    idxm = np.round((mids - 14) / 0.05).astype(int)

    per_a = {}
    grid_rows = []
    for a in A_LIST:
        ta = time.time()
        K1 = make_K1(a)
        lg = np.array([np.log(K1(z)) for z in zgrid])
        dip = float(lg[idxm].mean() - lg[idxg].mean())
        # mass fraction within +-0.1 of gamma (full window to 280)
        z = np.array([p[0] for p in data[a]])
        w = np.array([p[1] for p in data[a]])
        m = z <= 280
        zm, wm = z[m], w[m]
        idx = np.clip(np.searchsorted(gam, zm), 1, len(gam) - 1)
        d = np.minimum(np.abs(zm - gam[idx - 1]), np.abs(zm - gam[idx]))
        frac = float(wm[d <= 0.1].sum() / wm.sum())
        unif = float(0.2 * len(gam) / 280.0)
        # V3: within-z-bin mean log w by distance bin
        lw = np.log(wm)
        bins = {}
        for lo, hi in ((10, 60), (120, 200)):
            sel = (zm >= lo) & (zm < hi)
            for blo, bhi in ((0.0, 0.1), (0.3, 0.7)):
                s2 = sel & (d >= blo) & (d < bhi)
                if s2.sum() > 3:
                    bins[f"z{lo}-{hi}_d{blo}-{bhi}"] = float(lw[s2].mean())
        per_a[f"{a:g}"] = {
            "valley_depth": dip,
            "logK_at_gamma": float(lg[idxg].mean()),
            "logK_at_midpoints": float(lg[idxm].mean()),
            "mass_frac_pm0.1": frac,
            "uniform_expectation": unif,
            "mass_ratio_vs_uniform": frac / unif,
            "within_bin_meanlogw": bins,
            "elapsed_s": round(time.time() - ta, 1),
        }
        print(f"a={a:g}: dip={dip:.4f}, massfrac={frac:.4f} "
              f"({per_a[f'{a:g}']['elapsed_s']}s)", flush=True)
        for zz, ll in zip(zgrid, lg):
            grid_rows.append((a, zz, ll))

    # V4: saturation fit Delta(a) = Dinf - c/a
    av = np.array(A_LIST)
    dv = np.array([per_a[f"{a:g}"]["valley_depth"] for a in A_LIST])
    Afit = np.vstack([np.ones_like(av), -1.0 / av]).T
    Dinf, c = np.linalg.lstsq(Afit, dv, rcond=None)[0]
    resid = dv - (Dinf - c / av)
    print(f"V4: Delta_inf = {Dinf:.3f}, c = {c:.3f}, "
          f"max fit resid {np.abs(resid).max():.4f}", flush=True)

    checks = {
        "V1_valleys_at_gamma": bool(np.all(dv > 1.5)),
        "V2_mass_concentrated": bool(np.all(
            [per_a[f"{a:g}"]["mass_frac_pm0.1"] > 0.5 for a in A_LIST])),
        "V4_fit_quality": bool(np.abs(resid).max() < 0.1),
    }

    with open(CSV, "w", newline="") as f:
        wcsv = csvmod.writer(f)
        wcsv.writerow(["a", "z", "logK"])
        for a, zz, ll in grid_rows:
            wcsv.writerow([f"{a:g}", f"{zz:.3f}", f"{ll:.6f}"])

    meta = {
        "experiment": "E-022b",
        "task": "2.10 analysis: K-diagonal valleys + mass concentration",
        "script": "research/numerics/scripts/E-022b-valley-analysis.py",
        "checks": checks,
        "key_values": {**per_a,
                       "V4_saturation_fit": {"Delta_inf": float(Dinf),
                                             "c": float(c),
                                             "max_resid": float(
                                                 np.abs(resid).max())},
                       "valley_depths": dict(zip([str(a) for a in av],
                                                 dv.tolist()))},
        "elapsed_seconds": round(time.time() - t0, 1),
        "timestamp_utc": datetime.now(timezone.utc).isoformat(),
    }
    JSON.write_text(json.dumps(meta, indent=2))
    print(f"wrote {CSV.name}, {JSON.name}; elapsed "
          f"{meta['elapsed_seconds']}s", flush=True)
    return 0 if all(checks.values()) else 1


if __name__ == "__main__":
    sys.exit(main())