From 2f8267c53f0cf8100c4abfec212f2c25bbd047b3 Mon Sep 17 00:00:00 2001 From: muqiuhan Date: Fri, 31 Oct 2025 14:55:21 +0000 Subject: deploy: d9da638722c5bde9fa34c09e753e78b9f4817d76 --- search.xml | 39 ++++++++++++++++++++++++++------------- 1 file changed, 26 insertions(+), 13 deletions(-) (limited to 'search.xml') diff --git a/search.xml b/search.xml index 0c14fb16..eda049da 100644 --- a/search.xml +++ b/search.xml @@ -3779,6 +3779,19 @@ NestJS 依赖其底层 HTTP 适配器(默认为 Express)来解析传入的

希望我们再见时,可以向你讲述沿途风景,讲述我感受到的世界与爱。

也希望你在那边一切都好。

在星空的另一端,思念从未停止。

+]]> + + gallery + + + + 二〇二五年十月三十一日 + /2025/10/31/%E4%BA%8C%E3%80%87%E4%BA%8C%E4%BA%94%E5%B9%B4%E5%8D%81%E6%9C%88%E4%B8%89%E5%8D%81%E4%B8%80%E6%97%A5/ + 傍晚的海风带着盐的咸味和鱼网的腥气吹上岸。她独自站在礁石上眺望。巨大的海面起伏不定,深蓝的尽头与灰暗的天空交融成一个模糊的线。巨大的落日悬浮其上,像一颗即将坠入海面的橙红心脏。霞光将她的脸庞染成暖色。海风掀起她披在肩上的丝巾,丝巾像一面旗帜在身后猎猎作响。她深深吸了一口气,咸冷的空气涌入肺腑,带着一种辽阔的清醒。

+

回屋的时候,月亮正上来。阳台上的玻璃亮得像刚刚下过一场雨。她伸手擦了一下,手心一片清凉。她抬头,看见那只鸟又停在那里,歪着头看着她,然后起飞。影子一划而过,落在她的肩上,像一句轻不可闻的话。

+

她忽然笑了一下,像把窗纱上的一个小结解开。她说:“我替你把玻璃擦亮了。你也在替我把风擦亮。”屋里很安静,灯温柔地照着。她把手伸到光里,让手指被照成透明。透明的东西容易破碎,却也比别的更亮。

+

时间会带走了一个人,也带走了他的呼吸,他的声音,他掌心的温度。但似乎又留下了些什么

+

光的颗粒在空气里浮动,在记忆里游走,她闭上眼睛,光从睫毛上滑过,像许多个早晨,像许多个傍晚,像她们再次相遇的无数个灿然的瞬间。她在其中走走停停,像一粒微尘,又像一颗星。

]]>
gallery @@ -6125,19 +6138,6 @@ NestJS 依赖其底层 HTTP 适配器(默认为 Express)来解析传入的 Life
- - 隐藏一些OCaml Effect的机制,让其语法在精神上更接近delimcc - /2023/06/28/%E9%9A%90%E8%97%8F%E4%B8%80%E4%BA%9BOCaml-Effect%E7%9A%84%E6%9C%BA%E5%88%B6%EF%BC%8C%E8%AE%A9%E5%85%B6%E8%AF%AD%E6%B3%95%E5%9C%A8%E7%B2%BE%E7%A5%9E%E4%B8%8A%E6%9B%B4%E6%8E%A5%E8%BF%91delimcc/ - delimcc_of_fxhandler这个库在OCaml5的effect handlers上实现了一些delimcc原语(shift/reset, control/prompt这些):

-
let p = new_prompt () in
assert ([] = push_prompt p (fun () ->
1::2::take_subcont p (fun _k -> [])));
assert ([1;2] = push_prompt p (fun () ->
1::2::take_subcont p (fun k -> push_subcont k [])));
assert (135 =
let p1 = new_prompt () in
let p2 = new_prompt () in
let p3 = new_prompt () in
let pushtwice sk =
sk (fun () ->
sk (fun () ->
shift0 p2 (fun sk2 -> sk2 (fun () ->
sk2 (fun () -> 3))) ()))
in
push_prompt p1 (fun () ->
push_prompt p2 (fun () ->
push_prompt p3 (fun () -> shift0 p1 pushtwice ()) + 10) + 1) + 100);

print_endline "Success!"
-

另外, avsm这里可以看到一些OCaml的Effect Syntax进展。

-

还有 multi-shot continuations in OCaml,在这个仓库里面还讨论了一些有趣的问题,例如,OCaml 编译器和runtime会做出一些假设从而进行一些优化,这些优化在使用multi-shot continutation时是不可取的(或完全错误的)。编译器优化导致错误的一个例子是堆到栈的转换,例如:

-
(* An illustration of how the heap to stack optimisation is broken.
* This example is adapted from de Vilhena and Pottier (2021).
* file: heap2stack.ml
* compile: ocamlopt -I $(opam var lib)/multicont multicont.cmxa heap2stack.ml
* run: ./a.out *)

(* We first require a little bit of setup. The following declares an
operation `Twice' which we use to implement multiple returns. *)
type _ Effect.t += Twice : unit Effect.t

(* The handler `htwice' interprets `Twice' by simply invoking its
continuation twice. *)
let htwice : (unit, unit) Effect.Deep.handler
= { retc = (fun x -> x)
; exnc = (fun e -> raise e)
; effc = (fun (type a) (eff : a Effect.t) ->
let open Effect.Deep in
match eff with
| Twice -> Some (fun (k : (a, _) continuation) ->
continue (Multicont.Deep.clone_continuation k) ();
continue k ())
| _ -> None) }

(* Now for the interesting stuff. In the code below, the compiler will
perform an escape analysis on the reference `i' and deduce that it
does not escape the local scope, because it is unaware of the
semantics of `perform Twice', hence the optimiser will transform
`i' into an immediate on the stack to save a heap allocation. As a
consequence, the assertion `(!i = 1)' will succeed twice, whereas
it should fail after the second return of `perform Twice'. *)
let heap2stack () =
Effect.Deep.match_with
(fun () ->
let i = ref 0 in
Effect.perform Twice;
i := !i + 1;
Printf.printf "i = %d\n%!" !i;
assert (!i = 1))
() htwice

(* The following does not trigger an assertion failure. *)
let _ = heap2stack ()

(* To fix this issue, we can wrap reference allocations in an instance
of `Sys.opaque_identity'. However, this is not really a viable fix
in general, as we may not have access to the client code that
allocates the reference! *)
let heap2stack' () =
Effect.Deep.match_with
(fun () ->
let i = Sys.opaque_identity (ref 0) in
Effect.perform Twice;
i := !i + 1;
Printf.printf "i = %d\n%!" !i;
assert (!i = 1))
() htwice

(* The following triggers an assertion failure. *)
let _ = heap2stack' ()
-]]>
- - Technique - -
金匮要略 /2023/03/04/%E9%87%91%E5%8C%AE%E8%A6%81%E7%95%A5/ @@ -7405,6 +7405,19 @@ NestJS 依赖其底层 HTTP 适配器(默认为 Express)来解析传入的 Medicine + + 隐藏一些OCaml Effect的机制,让其语法在精神上更接近delimcc + /2023/06/28/%E9%9A%90%E8%97%8F%E4%B8%80%E4%BA%9BOCaml-Effect%E7%9A%84%E6%9C%BA%E5%88%B6%EF%BC%8C%E8%AE%A9%E5%85%B6%E8%AF%AD%E6%B3%95%E5%9C%A8%E7%B2%BE%E7%A5%9E%E4%B8%8A%E6%9B%B4%E6%8E%A5%E8%BF%91delimcc/ + delimcc_of_fxhandler这个库在OCaml5的effect handlers上实现了一些delimcc原语(shift/reset, control/prompt这些):

+
let p = new_prompt () in
assert ([] = push_prompt p (fun () ->
1::2::take_subcont p (fun _k -> [])));
assert ([1;2] = push_prompt p (fun () ->
1::2::take_subcont p (fun k -> push_subcont k [])));
assert (135 =
let p1 = new_prompt () in
let p2 = new_prompt () in
let p3 = new_prompt () in
let pushtwice sk =
sk (fun () ->
sk (fun () ->
shift0 p2 (fun sk2 -> sk2 (fun () ->
sk2 (fun () -> 3))) ()))
in
push_prompt p1 (fun () ->
push_prompt p2 (fun () ->
push_prompt p3 (fun () -> shift0 p1 pushtwice ()) + 10) + 1) + 100);

print_endline "Success!"
+

另外, avsm这里可以看到一些OCaml的Effect Syntax进展。

+

还有 multi-shot continuations in OCaml,在这个仓库里面还讨论了一些有趣的问题,例如,OCaml 编译器和runtime会做出一些假设从而进行一些优化,这些优化在使用multi-shot continutation时是不可取的(或完全错误的)。编译器优化导致错误的一个例子是堆到栈的转换,例如:

+
(* An illustration of how the heap to stack optimisation is broken.
* This example is adapted from de Vilhena and Pottier (2021).
* file: heap2stack.ml
* compile: ocamlopt -I $(opam var lib)/multicont multicont.cmxa heap2stack.ml
* run: ./a.out *)

(* We first require a little bit of setup. The following declares an
operation `Twice' which we use to implement multiple returns. *)
type _ Effect.t += Twice : unit Effect.t

(* The handler `htwice' interprets `Twice' by simply invoking its
continuation twice. *)
let htwice : (unit, unit) Effect.Deep.handler
= { retc = (fun x -> x)
; exnc = (fun e -> raise e)
; effc = (fun (type a) (eff : a Effect.t) ->
let open Effect.Deep in
match eff with
| Twice -> Some (fun (k : (a, _) continuation) ->
continue (Multicont.Deep.clone_continuation k) ();
continue k ())
| _ -> None) }

(* Now for the interesting stuff. In the code below, the compiler will
perform an escape analysis on the reference `i' and deduce that it
does not escape the local scope, because it is unaware of the
semantics of `perform Twice', hence the optimiser will transform
`i' into an immediate on the stack to save a heap allocation. As a
consequence, the assertion `(!i = 1)' will succeed twice, whereas
it should fail after the second return of `perform Twice'. *)
let heap2stack () =
Effect.Deep.match_with
(fun () ->
let i = ref 0 in
Effect.perform Twice;
i := !i + 1;
Printf.printf "i = %d\n%!" !i;
assert (!i = 1))
() htwice

(* The following does not trigger an assertion failure. *)
let _ = heap2stack ()

(* To fix this issue, we can wrap reference allocations in an instance
of `Sys.opaque_identity'. However, this is not really a viable fix
in general, as we may not have access to the client code that
allocates the reference! *)
let heap2stack' () =
Effect.Deep.match_with
(fun () ->
let i = Sys.opaque_identity (ref 0) in
Effect.perform Twice;
i := !i + 1;
Printf.printf "i = %d\n%!" !i;
assert (!i = 1))
() htwice

(* The following triggers an assertion failure. *)
let _ = heap2stack' ()
+]]>
+ + Technique + +
领域驱动设计中的“聚合根” /2025/03/13/%E9%A2%86%E5%9F%9F%E9%A9%B1%E5%8A%A8%E8%AE%BE%E8%AE%A1%E4%B8%AD%E7%9A%84%E2%80%9C%E8%81%9A%E5%90%88%E6%A0%B9%E2%80%9D/ -- cgit v1.2.3