有没有办法将函数的输出记忆到磁盘?
我有一个功能
def getHtmlOfUrl(url):
... # expensive computation
Run Code Online (Sandbox Code Playgroud)
并希望做类似的事情:
def getHtmlMemoized(url) = memoizeToFile(getHtmlOfUrl, "file.dat")
Run Code Online (Sandbox Code Playgroud)
然后调用getHtmlMemoized(url),以便为每个url只执行一次昂贵的计算.
使用CSS和flexbox,我不明白如何给div"a"和"b"赋予相同的高度.我需要b变得更高,以匹配一个高度.换句话说,灰色框应该与红色框一样高.
我的理解是,它足以设置flex:1为a和b,以使它们具有相同的高度.但事实并非如此.
我试图设置flex-basis:0为"a"和"b",但内容被截断.我不能截断一个,我需要扩大.
#cont1{
display:flex;
flex-direction:column;
}
#a{
background-color:red;
flex:1;
}
#b{
background-color:grey;
flex:1;
}Run Code Online (Sandbox Code Playgroud)
<div id="cont1">
<div id="a">
<h1>title</h1>
<h1>title</h1>
<h1>title</h1>
<h1>title</h1>
<h1>title</h1>
<h1>title</h1>
</div>
<div id="b">
short text
</div>
</div>Run Code Online (Sandbox Code Playgroud)
有人可以解释为什么这会造成僵局,以及如何解决它?
txtLog.AppendText("We are starting the thread" + Environment.NewLine);
var th = new Thread(() =>
{
Application.Current.Dispatcher.Invoke(new Action(() => // causes deadlock
{
txtLog.AppendText("We are inside the thread" + Environment.NewLine); // never gets printed
// compute some result...
}));
});
th.Start();
th.Join(); // causes deadlock
// ... retrieve the result computed by the thread
Run Code Online (Sandbox Code Playgroud)
说明:我需要我的辅助线程来计算结果,并将其返回到主线程。但是辅助线程也必须将调试信息写入日志;并且日志在 wpf 窗口中,因此线程需要能够使用 dispatcher.invoke()。但是在我执行 Dispatcher.Invoke 的那一刻,发生了死锁,因为主线程正在等待辅助线程完成,因为它需要结果。
我需要一个模式来解决这个问题。请帮我重写这段代码。(请编写实际代码,不要只说“使用 BeginInvoke”)。谢谢你。
另外,理论上,我不明白一件事:只有当两个线程以不同的顺序访问两个共享资源时,才会发生死锁。但在这种情况下,实际资源是什么?一种是图形用户界面。但另一个是什么?我看不到。
而死锁通常是通过强加线程只能以精确的顺序锁定资源的规则来解决的。我已经在其他地方这样做了。但是在这种情况下我怎么能强加这个规则,因为我不明白实际的资源是什么?
编辑:这原来是一个 F# 错误,可以通过使用自定义选项类型而不是 Fsharp 的“选项”来解决。
在 F# 中,我尝试使用 Async.AwaitTask 调用 .net 任务。该任务抛出异常,我似乎无法使用 try-catch 或 Async.Catch 捕获它。而且我知道没有其他方法可以捕获异常。解决办法是什么?问题的原因是什么?感谢您的任何解释。
以下是一些测试代码,显示我未能捕获 DownloadStringTaskAsync 引发的异常:
open System
open System.Net
[<EntryPoint>]
let main argv =
let test =
async{
let! exc = Async.Catch( async{
try
let w = new Net.WebClient();
let! str = Async.AwaitTask (w.DownloadStringTaskAsync "") // throws ArgumentException
return Some str
with
| _ ->
return None // not caught
}
)
match exc with
| Choice1Of2 r -> return r
| Choice2Of2 ext -> …Run Code Online (Sandbox Code Playgroud) 这个问题是关于函数式编程的.示例代码在F#中.
假设我有一个简单的函数f:
let f x =
x + 1
Run Code Online (Sandbox Code Playgroud)
现在(由于我不想解释,与线程相关的原因)我必须将f转换为具有continuation的函数:
let f x cont =
cont (x+1)
Run Code Online (Sandbox Code Playgroud)
现在我必须重写所有调用f的函数,这些函数将不再编译.
例如,如果我有这个功能
let g x =
let res = f x
res + 2
Run Code Online (Sandbox Code Playgroud)
我必须重写g as
let g x cont =
f x (fun res ->
cont (res + 2) )
Run Code Online (Sandbox Code Playgroud)
这已经变得复杂了,但仍然是可以管理的.
但问题是:如何重写以下代码?
let lmapped = [ for x in l do
let res = f x
yield res + 1 ]
if List.isEmpty lmapped then
...
Run Code Online (Sandbox Code Playgroud)
有没有一种简单的方法来重写它?(可能避免使用显式递归函数,例如"let rec ...")谢谢
f# ×2
asynchronous ×1
c# ×1
css ×1
css3 ×1
deadlock ×1
dispatcher ×1
exception ×1
flexbox ×1
html ×1
memoization ×1
ocaml ×1
python ×1
wpf ×1