Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/fsharp/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何处理异常输入并停止在F#中运行函数的其余部分?_F# - Fatal编程技术网

如何处理异常输入并停止在F#中运行函数的其余部分?

如何处理异常输入并停止在F#中运行函数的其余部分?,f#,F#,我一直在学习F#,我正在用它写一个工具。除了我需要处理无效输入或异常情况外,一切正常 在F#中,推荐的处理方法是什么?根据我的函数的构造和使用方式,我不确定如何发回一条消息,告诉调用函数调用失败是由于输入错误,类似于C#的循环continue需要发生 我因失去归宿而痛苦。我可以从F#函数的任意位置返回,还是必须在最后一行 这里是我的一些代码的一个例子,其中输入在某些情况下基本上是空的,我正在检测到这一点。我需要防止流程中随后的步骤运行 let SchemaQueryString s =

我一直在学习F#,我正在用它写一个工具。除了我需要处理无效输入或异常情况外,一切正常

在F#中,推荐的处理方法是什么?根据我的函数的构造和使用方式,我不确定如何发回一条消息,告诉调用函数调用失败是由于输入错误,类似于C#的循环continue需要发生

我因失去归宿而痛苦。我可以从F#函数的任意位置返回,还是必须在最后一行

这里是我的一些代码的一个例子,其中输入在某些情况下基本上是空的,我正在检测到这一点。我需要防止流程中随后的步骤运行

let SchemaQueryString s =
    let sqsValid s = 
        let Strcat (x : string) (y : string) = x + ", " + y;
        let RecFieldName (x : MeasurementRecord) = x.FieldName;    
        let mapr = List.map RecFieldName s.MeasurementTypes;
        let cores = List.reduce Strcat mapr;
        "SELECT ProductionCode, TestTime, " + cores + " FROM " + s.TemplateName + " ORDER BY ProductionCode, TestTime";

    match s.MeasurementTypes.Length with
    | 0 -> ""
    | _ -> sqsValid s;

let TemplateMigration tcs rr =
    let sql = SchemaQueryString tcs;
    let sqlc = new SqlCommand(sql, QCOld);
    let sqldr = sqlc.ExecuteReader();
    ignore (sqldr.Read());
    ...
我需要中止TemplateMigration函数,并在sql变量与“”匹配时立即返回。或者构造某种联合类型,该类型指示无法构造sql查询字符串,因为对于特定情况,无法进行构造


谢谢你的帮助。我正在逐渐了解这种语言,我非常喜欢它,但我正在努力解决它的某些方面,我不知道如何用函数思想取代我关于如何做某事的过程性思想。

与其他语言一样,您可以随时返回。插入一个条件,返回坏数据的特殊值(-1,“错误”等),继续处理,否则返回好数据


或者使用F#s。

与其他语言一样,您可以随时返回。插入一个条件,返回坏数据的特殊值(-1,“错误”等),继续处理,否则返回好数据


或者在第一次使用函数式语言时使用F#。

许多人会误以为一切都是表达式。这意味着使用控制流表达式执行控制流

那么,语句和表达式之间有什么区别呢

语句没有值,即它不是类型的实例。表达式有一个值(即使该值是特殊类型的
单元
,它有一个不表示值的实例
()

在过程语言中,我们使用语句来控制执行流程,因此:

class Program
{
    static void Main(string[] args)
    {
        string str;

        if (DateTime.Now.DayOfWeek == DayOfWeek.Monday)
            return;
        else if (args.Length >= 2)
            str = args[1];
        else
            str = "Hello";

        Console.WriteLine(str);
    }
}
这里我们定义了一个
string
类型的变量
str
,它的值为
null
。然后,我们要么忽略它并
返回
,如果是星期一,分配
参数[1]
(如果可用),要么
“Hello”
,否则打印它

当控制流语句只有几行时,这种编程是相当安全的。然而,一旦语句变得超过一页长,或者变得复杂和嵌套,我们就更有可能引入错误,通常是错误

纯函数式语言使用控制流表达式。这意味着
if
表达式有一个值!让我们慢慢实现前一个代码示例中的控件。首先让我们来处理分配字符串
str

let str =
    if args.Length >= 2 then
        args.[1]
    else 
        "Hello"
这里我们看到,我们直接将
if
表达式的值绑定到
str
if
表达式的两个分支(子表达式)必须计算为
字符串类型的实例。我们不能忘记给字符串赋值,因为如果我们尝试,编译器会抛出一个错误

但在很多情况下,我们希望在控制流的不同分支中做不同类型的事情。在我们的例子中,如果是星期一,我们什么都不想做。这就是受歧视工会的力量发挥作用的地方。这些允许我们将异构类型组合成一个整体,保留了基于表达式的语言在各个级别对代码进行类型检查的能力

在本例中,我们不需要创建新的联合类型,因为
选项
类型已经包含此功能。因此,我们改写如下:

open System

[<EntryPoint>]
let Main args =

    let str =
        if DateTime.Now.DayOfWeek = DayOfWeek.Monday then
            None
        elif args.Length >= 2 then
            Some(args.[1])
        else 
            Some("Hello")

    match str with
    | Some(str) -> Console.WriteLine(str)
    | None      -> ()

    Environment.ExitCode 
但是,最好从
SchemaQueryString

let SchemaQueryString s =
    ... // Elided

    match s.MeasurementTypes.Length with
    | 0 -> None
    | _ -> Some(sqsValid s)

在整个代码中“传播”强类型值。

当第一次使用函数式语言时,许多人突然想到一切都是表达式。这意味着使用控制流表达式执行控制流

那么,语句和表达式之间有什么区别呢

语句没有值,即它不是类型的实例。表达式有一个值(即使该值是特殊类型的
单元
,它有一个不表示值的实例
()

在过程语言中,我们使用语句来控制执行流程,因此:

class Program
{
    static void Main(string[] args)
    {
        string str;

        if (DateTime.Now.DayOfWeek == DayOfWeek.Monday)
            return;
        else if (args.Length >= 2)
            str = args[1];
        else
            str = "Hello";

        Console.WriteLine(str);
    }
}
这里我们定义了一个
string
类型的变量
str
,它的值为
null
。然后,我们要么忽略它并
返回
,如果是星期一,分配
参数[1]
(如果可用),要么
“Hello”
,否则打印它

当控制流语句只有几行时,这种编程是相当安全的。然而,一旦语句变得超过一页长,或者变得复杂和嵌套,我们就更有可能引入错误,通常是错误

纯函数式语言使用控制流表达式。这意味着
if
表达式有一个值!让我们慢慢实现前一个代码示例中的控件。首先让我们来处理分配字符串
str

let str =
    if args.Length >= 2 then
        args.[1]
    else 
        "Hello"
这里我们看到,我们直接将
if
表达式的值绑定到
str
if
表达式的两个分支(子表达式)必须计算为
字符串类型的实例。我们不能忘记给字符串赋值,因为如果我们尝试,编译器会抛出一个错误

但似乎有一个
match SchemaQueryString tcs with
| None -> ()
| Some(sql) -> ... // rest of function