valuesof() ("M" Reference)

[This content is no longer valid. For the latest information on "M", "Quadrant", SQL Server Modeling Services, and the Repository, see the Model Citizen blog.]

This function returns the values stored in a container such as a collection or a list.

valuesof(variable reference)

Parameters

A variable reference is passed to the function. This variable often references a container structure, but not necessarily.

Property Value/Return Value

The function returns the values stored in a container. If the variable references a literal, nothing is returned.

Exceptions

valuesof() must be used inside a list or collection constructor. Its use in any other context is not allowed.

Remarks

This function is used to flatten nested output structures. The valuesof function extracts the successors of a variable reference. In a highly nested structure, it reduces the number of nesting levels by removing the top-most level and returning the individual values that it contains. Of course many of these values may themselves be nested collections.

The call to the function must be enclosed inside collection or list delimitters.

Example

The following code uses a common idiom for expressing lists in a recursive style. The output that results from this is highly nested and reflects exactly the parse path taken through the recursion. It is likely, however, that the recursion parse path is not of interest to the application that receives the data. Using the valuesof function can eliminate what may be redundant levels of nesting.

This code takes as its input a list of method names, each prefixed by the string "METHOD ". It transforms this input data into a graph structure.

The following is the original code. Note the comment on the syntax rule named Methods.

module Methods 
{
   language Parser
   {
        syntax Main       = Methods;
        syntax Methods    = ts:Methods t:Method //=> [valuesof(ts), t]
                          | Method;
        syntax Method     = ml:MethodLit n:Name;
        token MethodLit   = "METHOD";
        syntax Name       = chs;
        token Char  = "A".."Z" | "a".."z"  | "0".."9";
        token chs   = Char+;             
        token LF                = "\u000A";
        token CR                = "\u000D";
        token Space             = "\u0020";
        interleave Whitespace   = Space | LF | CR;       
   } 
}

The following is some sample data.

METHOD add  
METHOD subtract
METHOD multiply
METHOD divide

The parser transforms this input into the following output. Note how the Methods node is nested and repeated because of the definition in the corresponding syntax rule.

Main[
  Methods[
    Methods[
      Methods[
        Methods[
          Method[
            "METHOD",
            Name[
              "add"
            ]
          ]
        ],
        Method[
          "METHOD",
          Name[
            "subtract"
          ]
        ]
      ],
      Method[
        "METHOD",
        Name[
          "multiply"
        ]
      ]
    ],
    Method[
      "METHOD",
      Name[
        "divide"
      ]
    ]
  ]
]

If the comment symbol ("//") is removed from the Methods syntax rule, each instance of the Methods has its content recursively promoted up a level, and we get the following output.

In a real application, one would very likely eliminate the occurence of the "METHOD" literal from the output, and the output data structure would be more complex than this simple sample.

Main[
  [
    Method[
      "METHOD",
      Name[
        "add"
      ]
    ],
    Method[
      "METHOD",
      Name[
        "subtract"
      ]
    ],
    Method[
      "METHOD",
      Name[
        "multiply"
      ]
    ],
    Method[
      "METHOD",
      Name[
        "divide"
      ]
    ]
  ]
]

See Also

Concepts

Custom Rule Projections