yql-15485.sql 2.8 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586
  1. /* syntax version 1 */
  2. /* postgres can not */
  3. $ages = [
  4. <|suffix: "0-0.5"u, begin: 0.f, end: 0.5f|>,
  5. <|suffix: "0.5-1"u, begin: 0.5f, end: 1.f|>,
  6. <|suffix: "1-3"u , begin: 1.f, end: 3.f|>,
  7. <|suffix: "3-5"u , begin: 3.f, end: 5.f|>,
  8. <|suffix: "5-7"u , begin: 5.f, end: 7.f|>,
  9. <|suffix: "7-9"u , begin: 7.f, end: 9.f|>,
  10. <|suffix: "9-12"u , begin: 9.f, end: 12.f|>,
  11. <|suffix: "12-14"u, begin: 12.f, end: 14.f|>,
  12. <|suffix: "14-16"u, begin: 14.f, end: 16.f|>,
  13. <|suffix: "16+"u , begin: 16.f, end: 18.f|>,
  14. ];
  15. $interval_fits_in = ($interval, $other) -> {
  16. $length = $interval.end - $interval.begin;
  17. RETURN IF(
  18. $interval.end <= $other.begin OR $interval.begin >= $other.end,
  19. 0.f,
  20. IF(
  21. $interval.begin >= $other.begin AND $interval.end <= $other.end, -- interval is completely within other
  22. 1.f,
  23. IF(
  24. $interval.begin <= $other.begin AND $interval.end >= $other.end, -- other is completely within the interval
  25. ($other.end - $other.begin) / $length,
  26. IF(
  27. $interval.begin < $other.begin,
  28. ($interval.end - $other.begin) / $length,
  29. ($other.end - $interval.begin) / $length
  30. )
  31. )
  32. )
  33. );
  34. };
  35. $age_suffixes = ($interval, $age_segments) -> {
  36. RETURN IF(
  37. $interval.end - $interval.begin > 10.f OR $interval.end - $interval.begin < 1e-4f,
  38. [NULL],
  39. ListFilter(
  40. ListMap(
  41. $age_segments,
  42. ($i) -> {
  43. RETURN <|age_suffix: ":Age:"u || $i.suffix, age_weight: $interval_fits_in($interval, $i)|>
  44. }
  45. ),
  46. ($i) -> {
  47. RETURN $i.age_weight > 1e-4f;
  48. }
  49. )
  50. );
  51. };
  52. $data = (
  53. SELECT
  54. *
  55. FROM
  56. (
  57. SELECT
  58. puid,
  59. ts,
  60. boys ?? False AS boys,
  61. girls ?? False AS girls,
  62. min_age ?? 0.f AS min_age,
  63. max_age ?? 18.f AS max_age
  64. FROM
  65. AS_TABLE([
  66. <|puid: 1, ts: 123, boys: True, girls: False, min_age: 1.f, max_age: 2.f|>,
  67. <|puid: 2, ts: 123, boys: True, girls: False, min_age: NULL, max_age: NULL|>,
  68. <|puid: 3, ts: 123, boys: NULL, girls: NULL, min_age: 1.f, max_age: 2.f|>,
  69. <|puid: 4, ts: 123, boys: True, girls: True, min_age: 1.f, max_age: 2.f|>,
  70. <|puid: 5, ts: 123, boys: True, girls: True, min_age: 1.f, max_age: 5.f|>,
  71. <|puid: 6, ts: 123, boys: True, girls: False, min_age: 1.f, max_age: 2.f|>,
  72. ])
  73. )
  74. WHERE boys OR girls OR min_age > 0.f OR max_age < 18.f
  75. );
  76. SELECT
  77. puid,
  78. $age_suffixes(<|begin: min_age, end: max_age|>, $ages) AS age_suffixes,
  79. <|begin: min_age, end: max_age|> as interval
  80. FROM $data;