Reputation: 2891
I am new to programming and F# is my first language.
I followed the advice given to me in this thread to use NewtonSoft.Json. Here are some relevant parts of my code:
[<CLIMutable>]
[<JsonObject(MemberSerialization=MemberSerialization.OptOut)>]
type FighterSummary =
{
mutable fighter: string;
mutable record: string option;
mutable reach: float option;
mutable stance: string option;
}
let fighterFilesDir = @"G:\Fighter Pages"
let fighterFiles = Directory.GetFiles(fighterFilesDir)
let fighterGroups = splitArrayIntoGroups fighterFiles 50
for group in fighterGroups do
let fighterStats = seq {
for file in group do
let html = File.ReadAllText(file)
let fighterOverview = getFighterSummary html
printfn "Extracted %s's overview." (Path.GetFileNameWithoutExtension(file))
yield fighterOverview
}
|> Seq.toArray
let fileName = Path.GetFileNameWithoutExtension(group.[0]) + " -- " + Path.GetFileNameWithoutExtension(group.[group.Count() - 1])
let saveFilePath = @"G:\Fighter Data JSON Files\" + fileName + ".json"
File.WriteAllText(saveFilePath, JsonConvert.SerializeObject(fighterStats))
I have tested the functions getFighterSummary and splitArrayIntoGroups using F# Interactive. They work splendidly.
When I save a record of type FighterSummary to JSON, I see something like this for each different fighter:
{"fighter@": "Alessio Sakara",
"record@": {
"Case": "Some",
"Fields": ["19-11-0 (1 NC)"]
},
"reach@": {
"Case": "Some",
"Fields": [182.88]
},
"stance@": {
"Case": "Some",
"Fields": ["Orthodox"]
},
"fighter": "Alessio Sakara",
"record": {
"Case": "Some",
"Fields": ["19-11-0 (1 NC)"]
},
"reach": {
"Case": "Some",
"Fields": [182.88]
},
"stance": {
"Case": "Some",
"Fields": ["Orthodox"]}
The information about each fighter is saved twice -- the first time with an "@" at the end of each field name, the second time without.
What I want instead is for the information about the fighter to be saved only once, without "@" at the end of each field name.
I have read the answers here, in response to a question posted by someone who faced a similar problem. I have tried implementing the suggestions provided there, but they didn't work.
I would appreciate it if anyone can help me with this problem. Thank you.
EDIT:
I also have trouble deserializing JSON. When I run
JsonConvert.DeserializeObject<FighterSummary>(File.ReadAllText(@"G:\Fighter Data JSON Files\Fighters.json"))
I get the following error message:
System.Reflection.CustomAttributeFormatException: 'MemberSerialization' property specified was not found. ---> System.Reflection.CustomAttributeFormatException: 'MemberSerialization' property specified was not found.
Upvotes: 0
Views: 172
Reputation: 3838
Notice, that in the post you mentioned, they used [<CliMutable>]
but the members themselves were not mutable
. While looking at your code, I don't see, why you would need mutable
(in F#). The mutable
keyword allows assignment using <-
which is rarely used in F#. The [<CliMutable>]
is there, so that the compiled code is mutable, but it remains immutable in F# code.
This is sometimes useful when you want to use the record e.g. using reflection. And JSON.Net should be able to handle things, if you just [<CliMutable>]
but not make the mutable
keyword in F#.
Upvotes: 1