Deat alls,
Я пытаюсь работать с этими несколькими строками кода, но я действительно не знаю, почему 'myTreeNodes' список TreeNodes сбрасывается во время вызова 'extractData' процедуры.
Кажется, что я соблюдал все необходимые ограничения и хорошую практику, но что-то... я упустил!
Заранее большое спасибо за любое ваше предложение
ANN
let GetFactors =
let errorHeader = "Gasket Factor - List Retrieve"
let doc = new XmlDocument()
let myTreeNodes = List<TreeNode>.Empty
let readData (xmlNode:XmlNode) (treeNodes:List<TreeNode>) =
match xmlNode.Name with
| "GasketFactors" ->
let attribs = xmlNode.Attributes
if (attribs.Count > 0) then
let name = GetStringData "Version" attribs
printfn "GASKET FACTORS VERSION: '%s'" name
| "Gasket" ->
let attribs = xmlNode.Attributes
if (attribs.Count > 0) then
let name = GetStringData "Type" attribs
let mainNode = new TreeNode(name)
let treeNodes = mainNode :: treeNodes
printfn " - Type: %s " name
| "Data" ->
let attribs = xmlNode.Attributes
if (attribs.Count > 0) then
let parent = List.head treeNodes
let gskType = parent.Name
let gskSource = GetStringData "Source" attribs
let gskSubType = GetStringData "SubType" attribs
let gskMaterialGroup = GetStringData "Group" attribs
let gskMaterial = GetStringData "Material" attribs
let gskMaterialFiller = GetStringData "Filler" attribs
let gskMaterialLayers = GetStringData "Layers" attribs
let gsk_m =
let value = GetStringData "m" attribs
0.0
let gsk_y =
let value = GetStringData "y" attribs
0.0
let gskFactors = new Factors(gsk_m, gsk_y)
let gskService = GetStringData "Service" attribs
let gskUserNote = GetStringData "Note" attribs
let gskShow = GetBoolData "Show" attribs
let newGasket = new Gasket(gskSource, gskType, gskSubType,
gskMaterial, gskMaterialGroup, gskMaterialFiller, gskMaterialLayers,
gskFactors, new Geometry(),
gskService, gskUserNote, gskShow)
let childNode = new TreeNode(gskSubType)
childNode.Tag <- newGasket
parent.Nodes.Add(childNode) |> ignore
printfn " - Sub Type: %s " (newGasket.ToString())
| _ ->
printfn "%A" xmlNode
let rec extractData (xmlNode:XmlNode) (treeNodes:List<TreeNode>) =
if (xmlNode <> null) then
match xmlNode.NodeType with
| XmlNodeType.Element ->
readData xmlNode treeNodes
printfn "{TEXT: %s}" xmlNode.Value
if (xmlNode.HasChildNodes) then
extractData xmlNode.FirstChild treeNodes
else
let next = xmlNode.NextSibling
let parent = xmlNode.ParentNode
if (next <> null) then
extractData next treeNodes
else
extractData parent treeNodes
| XmlNodeType.Text | XmlNodeType.CDATA ->
printfn "{TEXT: %s}" xmlNode.Value
extractData xmlNode.NextSibling treeNodes
| XmlNodeType.Comment ->
printfn "{COMMENT: %s}" xmlNode.Value
extractData xmlNode.NextSibling treeNodes
| XmlNodeType.ProcessingInstruction | XmlNodeType.XmlDeclaration ->
printfn "{DECLARATION: %s = %s}" xmlNode.Name xmlNode.Value
extractData xmlNode.NextSibling treeNodes
| _ ->
printfn "{OTHER: %s = %s}" xmlNode.Name xmlNode.Value
extractData xmlNode.NextSibling treeNodes
else
()
try
doc.Load( Resources.GasketXMLFactorsPath )
with
| ex -> failwith (errorHeader + ": Not Possible to Load!" + ex.ToString())
extractData doc.FirstChild myTreeNodes
myTreeNodes
{GasketFactors Version="1.0.0.0"} {Gasket Type="Self-Energizing"} {Data Source="ASME" SubType="Welded" m="0.00" y="0.0 psi" /} {Data Source="ASME" SubType="Any" m="0.00" y="0.0 psi" /} {/Gasket} {Gasket Type="Vegetable Fibers"} {Data Source="ASME" SubType="Any" Material="Any" m="1.75" y="1100.0 psi" /} {/Gasket} {/GasketFactors}
Я не углублялся глубоко, но если
let myTreeNodes = List<TreeNode>.Empty
- это F # list <'T>, тогда он неизменяемый, и когда вы добавляете элемент в список - вы создаете новый список вместо изменения исходного. Вы можете либо на каждом шаге брать список источников и возвращать измененную версию, либо использовать изменяемую коллекцию, например System.Collections.Generic.List <'T> или System.Collections.Generic.LinkedList < 'T> для накопления изменений.