F#:跳出循环
F#: Breaking out of a loop
我是编程新手,F# 是我的第一语言。
我有一个 URL 的列表,当第一次访问时,它们要么返回 HTTP 错误 404,要么遇到网关超时。对于这些 URLs,我想再尝试访问它们 3 次。在这 3 次尝试结束时,如果仍然抛出 WebException 错误,我将假定 URL 不存在,并将其添加到包含所有无效 URL 的文本文件中s.
这是我的代码:
let tryAccessingAgain (url: string) (numAttempts: int) =
async {
for attempt = 1 to numAttempts do
try
let! html = fetchHtmlAsync url
let name = getNameFromPage html
let id = getIdFromUrl url
let newTextFile = File.Create(htmlDirectory + "\" + id.ToString("00000") + " " + name.TrimEnd([|' '|]) + ".html")
use file = new StreamWriter(newTextFile)
file.Write(html)
file.Close()
with
:? System.Net.WebException -> File.AppendAllText("G:\User\Invalid URLs.txt", url + "\n")
}
我已经在 F# Interactive 中测试了 fetchHtmlAsync、getNameFromPage 和 getIdFromUrl。他们都工作正常。
如果我成功下载了 URL 的 HTML 内容而没有使用全部 3 次尝试,显然我想立即跳出 for 循环。我的问题是:我该怎么做?
使用递归代替循环:
let rec tryAccessingAgain (url: string) (numAttempts: int) =
async {
if numAttempts > 0 then
try
let! html = fetchHtmlAsync url
let name = getNameFromPage html
let id = getIdFromUrl url
let newTextFile = File.Create(htmlDirectory + "\" + id.ToString("00000") + " " + name.TrimEnd([|' '|]) + ".html")
use file = new StreamWriter(newTextFile)
file.Write(html)
file.Close()
with
| :? System.Net.WebException ->
File.AppendAllText("G:\User\Invalid URLs.txt", url + "\n")
return! tryAccessingAgain url (numAttempts-1)
}
请注意,我无法对其进行测试,并且可能存在一些语法错误 - 抱歉,如果
正如我们所做的那样 - 您可能想像这样重写无效 url 的日志记录:
let rec tryAccessingAgain (url: string) (numAttempts: int) =
async {
if numAttempts <= 0 then
File.AppendAllText("G:\User\Invalid URLs.txt", url + "\n")
else
try
let! html = fetchHtmlAsync url
let name = getNameFromPage html
let id = getIdFromUrl url
let newTextFile = File.Create(htmlDirectory + "\" + id.ToString("00000") + " " + name.TrimEnd([|' '|]) + ".html")
use file = new StreamWriter(newTextFile)
file.Write(html)
file.Close()
with
| :? System.Net.WebException ->
return! tryAccessingAgain url (numAttempts-1)
}
这样它只会记录一次所有尝试
我是编程新手,F# 是我的第一语言。
我有一个 URL 的列表,当第一次访问时,它们要么返回 HTTP 错误 404,要么遇到网关超时。对于这些 URLs,我想再尝试访问它们 3 次。在这 3 次尝试结束时,如果仍然抛出 WebException 错误,我将假定 URL 不存在,并将其添加到包含所有无效 URL 的文本文件中s.
这是我的代码:
let tryAccessingAgain (url: string) (numAttempts: int) =
async {
for attempt = 1 to numAttempts do
try
let! html = fetchHtmlAsync url
let name = getNameFromPage html
let id = getIdFromUrl url
let newTextFile = File.Create(htmlDirectory + "\" + id.ToString("00000") + " " + name.TrimEnd([|' '|]) + ".html")
use file = new StreamWriter(newTextFile)
file.Write(html)
file.Close()
with
:? System.Net.WebException -> File.AppendAllText("G:\User\Invalid URLs.txt", url + "\n")
}
我已经在 F# Interactive 中测试了 fetchHtmlAsync、getNameFromPage 和 getIdFromUrl。他们都工作正常。
如果我成功下载了 URL 的 HTML 内容而没有使用全部 3 次尝试,显然我想立即跳出 for 循环。我的问题是:我该怎么做?
使用递归代替循环:
let rec tryAccessingAgain (url: string) (numAttempts: int) =
async {
if numAttempts > 0 then
try
let! html = fetchHtmlAsync url
let name = getNameFromPage html
let id = getIdFromUrl url
let newTextFile = File.Create(htmlDirectory + "\" + id.ToString("00000") + " " + name.TrimEnd([|' '|]) + ".html")
use file = new StreamWriter(newTextFile)
file.Write(html)
file.Close()
with
| :? System.Net.WebException ->
File.AppendAllText("G:\User\Invalid URLs.txt", url + "\n")
return! tryAccessingAgain url (numAttempts-1)
}
请注意,我无法对其进行测试,并且可能存在一些语法错误 - 抱歉,如果
正如我们所做的那样 - 您可能想像这样重写无效 url 的日志记录:
let rec tryAccessingAgain (url: string) (numAttempts: int) =
async {
if numAttempts <= 0 then
File.AppendAllText("G:\User\Invalid URLs.txt", url + "\n")
else
try
let! html = fetchHtmlAsync url
let name = getNameFromPage html
let id = getIdFromUrl url
let newTextFile = File.Create(htmlDirectory + "\" + id.ToString("00000") + " " + name.TrimEnd([|' '|]) + ".html")
use file = new StreamWriter(newTextFile)
file.Write(html)
file.Close()
with
| :? System.Net.WebException ->
return! tryAccessingAgain url (numAttempts-1)
}
这样它只会记录一次所有尝试