F#的Condtional表达式需要检查条件,分支为true,分支为false.例如:
let x =
if ("hello" = null)
then true
else false //error if else branch missing
Run Code Online (Sandbox Code Playgroud)
然而,当事情会很奇怪unit,又名(),参与.
let y =
if ("hello" = null)
then raise <| new ArgumentNullException()
else () //happy with or without else branch
Run Code Online (Sandbox Code Playgroud)
而且更简单:
let z =
if ("hello" = null)
then ()
else () //happy with or without else branch
Run Code Online (Sandbox Code Playgroud)
返回else时为什么不需要分支unit?
我每天都使用 F# Interactive,因此我喜欢从 cmd 启动它,而不仅仅是 Visual Studio 和 Visual Studio Code。为此,我FSHARPINSTALLDIR在 my 中调用了一个PATH指向C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\Common7\IDE\CommonExtensions\Microsoft\FSharp. 这使我只需键入即可fsi启动 F# 交互。
C# Interactive 安装在哪里,以便我可以做同样的事情?
我<LangVersion>preview</LangVersion>在我的项目文件中使用 F# 4.7 。
我有这样的类型:
type Record = {
Name : string
Description : string
FieldNotInterestedIn: int
}
Run Code Online (Sandbox Code Playgroud)
我想以类型安全的方式获取某些字段的名称,但不是全部。我知道我可以使用反射获取所有字段名称。
这是我想出的最简洁的代码。能不能再简洁点?
let certainFieldNames =
let r = Unchecked.defaultof<Record>
[
nameof r.Name
nameof r.Description
]
Run Code Online (Sandbox Code Playgroud) 在Windows中,F#的互动和F#编译器可执行文件被命名为fsi和fsc。在带有 Mono 的 Mac 上,它们被称为fsharpi和fsharpc。这是为什么?
使用命名参数调用 aDictionary的Add()方法在 F# 中有效。
let d = Dictionary<string, obj>()
d.Add(key = "five", value = 5)
let d2= Dictionary<obj, obj>()
d2.Add(key = "five", value = 5)
d2.Add(key = 5, value = 5)
Run Code Online (Sandbox Code Playgroud)
在 Polly 的Contextclass 中,有一个类似的Add()方法,有 2 个重载:
Add(key: obj, value: obj) : unit
Add(key: string, value: obj) : unit
Run Code Online (Sandbox Code Playgroud)
我可以通过以下所有方式使用它:
let c = Polly.Context()
c.Add("five", 5)
c.Add(5, 5)
c.Add(key = 5, value = 5)
Run Code Online (Sandbox Code Playgroud)
但不是这样,它说它无法在重载之间解析并且需要类型注释。
c.Add(key = "five", value = 5)
Run Code Online (Sandbox Code Playgroud)
为什么会这样,我该如何解决?
我想使用牛津(或串行)逗号将字符串集合加入单个字符串中。
给定
let ss = [ "a"; "b"; "c"; "d" ]
Run Code Online (Sandbox Code Playgroud)
我想要
"a, b, c, and d"
Run Code Online (Sandbox Code Playgroud)
这是我想出的。
let oxford (strings: seq<string>) =
let ss = Seq.toArray strings
match ss.Length with
| 0 -> ""
| 1 -> ss.[0]
| 2 -> sprintf "%s and %s" ss.[0] ss.[1]
| _ ->
let allButLast = ss.[0 .. ss.Length - 2]
let commaSeparated = System.String.Join(", ", allButLast)
sprintf "%s, and %s" commaSeparated (Seq.last ss)
Run Code Online (Sandbox Code Playgroud)
如何改善呢?
---编辑---
关于多次遍历序列的注释就很重要了。下面的两种实现都避免了转换为数组。
如果使用seq,我会很喜欢:
open System.Linq …Run Code Online (Sandbox Code Playgroud) 我有一个 .NET Core 2.2 控制台应用程序可以连接到 Azure 存储队列。它在我的电脑上工作,但我无法让它在公司代理后面工作。我需要做什么?(我对存储帐户名称和密钥以及代理主机名进行了匿名处理。)
.csproj:
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<LangVersion>8.0</LangVersion>
<NullableContextOptions>enable</NullableContextOptions>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.Azure.Management.Fluent" Version="1.21.0" />
<PackageReference Include="Microsoft.Azure.Storage.Queue" Version="10.0.1" />
</ItemGroup>
</Project>
Run Code Online (Sandbox Code Playgroud)
包装类:
using Microsoft.WindowsAzure.Storage;
using Microsoft.WindowsAzure.Storage.Queue;
using System.Threading.Tasks;
namespace Queue
{
public class Queue
{
public Queue(string connectionString, string queueName)
{
var storageAccount = CloudStorageAccount.Parse(connectionString);
var cloudQueueClient = storageAccount.CreateCloudQueueClient();
CloudQueue = cloudQueueClient.GetQueueReference(queueName);
}
private CloudQueue CloudQueue { get; }
public async Task<string> PeekAsync()
{
var m = await CloudQueue.PeekMessageAsync();
return m.AsString;
}
}
} …Run Code Online (Sandbox Code Playgroud) 我有一个用F#编写的控制台应用程序,面向.NET Framework 4.6.2.我构建的工件是MyApp.exe和FSharp.Core.dll.这个页面https://docs.microsoft.com/en-us/dotnet/fsharp/language-reference/compiler-options表明该—-standalone标志应该允许我生成一个独立的MyApp.exe.我如何在Visual Studio(2017)中或通过其他方式执行此操作?
我有一个使用静态解析类型参数的泛型函数
let inline divide a b = a / b
Run Code Online (Sandbox Code Playgroud)
签名 ^a -> ^a -> ^a
我可以创建一个包装函数
let log f =
let result = f()
printfn "Result: %A" result
result
Run Code Online (Sandbox Code Playgroud)
如果我然后创建一个像这样的函数
let loggedDivide a b = log (fun () -> divide a b)
Run Code Online (Sandbox Code Playgroud)
它的签名float -> float -> float代替^a -> ^a -> ^a,意思是
loggedDivide 2.0 5.0
loggedDivide 2 5 //error
Run Code Online (Sandbox Code Playgroud)
如何才能做到这一点?
注意,这样的事情忽略了尝试重用函数的重点
let logValue a = printfn "Result: %A" a
divide 2.0 5.0 |> logValue
divide 2 …Run Code Online (Sandbox Code Playgroud) 我有一些嵌套的歧视工会
type Job = Sniff | Guard
type Dog = Chihuahua | GermanShepherd of Job
Run Code Online (Sandbox Code Playgroud)
这是一个接受a Dog并返回a 的函数string。
let dogPrinter d =
match d with
| Chihuahua -> ""
| GermanShepherd g ->
match g with
| Sniff -> ""
| Guard -> ""
Run Code Online (Sandbox Code Playgroud)
我可以将第一个转换match为function语法:
let dogPrinter = function
| Chihuahua -> ""
| GermanShepherd g ->
match g with
| Sniff -> ""
| Guard -> ""
Run Code Online (Sandbox Code Playgroud)
如何将第二个转换match为function?
我在 Clojure REPL 并且我输入了一个值
user=> [:a :b :c]
[:a :b :c]
Run Code Online (Sandbox Code Playgroud)
我如何在以后的表达式中引用该值?
这是一个客户端Fable.Remoting示例,它打印异步函数的结果。
// Client code (Compiled to Javascript using Fable)
// ============
open Fable.Remoting.Client
let server = Proxy.create<IServer>
async {
let! length = server.getLength “hello”
do printfn “%d” length // 5
}
|> Async.StartImmediate
Run Code Online (Sandbox Code Playgroud)
我如何获得length价值?
f# ×10
.net ×3
c# ×2
.net-core ×1
azure ×1
clojure ×1
collections ×1
compilation ×1
csi ×1
elmish ×1
expression ×1
fable-f# ×1
fsi ×1
generics ×1
http-proxy ×1
inline ×1
logging ×1
macos ×1
mono ×1
nameof ×1
nothing ×1
null ×1
polly ×1
properties ×1
reflection ×1
string ×1