Ejemplo n.º 1
0
        /// <summary>
        /// Parses <see cref="TypeInfo"/> from string.
        /// <para>If faield to parsing, returns null.</para>
        /// </summary>
        /// <param name="typeText">String that indicates type (that matches <see cref="TypePattern"/>)</param>
        /// <returns><see cref="TypeInfo"/> parsed from string, or null</returns>
        protected static TypeInfo ParseType(string typeText)
        {
            typeText = EscapeMultiDimensionalArray(Regex.Replace(typeText, VarArgPattern, "[]"));
            var typeSegments = typeText.Split(new[] { '.' }, StringSplitOptions.RemoveEmptyEntries);

            if (!typeSegments.Any())
            {
                return(null);
            }

            // Extracts an outer class names, and its type arguments are removed
            var outerName = string.Join(".", typeSegments.Take(typeSegments.Count() - 1));

            outerName = TextAnalyzer.SplitWithDepth(outerName, "<", ">").Where(t => t.Depth == 0).Marge("<", ">");

            // Parses an inner class name (including its type arguments)
            var words = TextAnalyzer.SplitWithDepth(typeSegments.Last(), "<", ">")
                        .SplitEach(",")
                        .SplitEach("[")         // Use '[' as a separator, and ']' is treated as an array descriptor.
                        .Where(w => !string.IsNullOrWhiteSpace(w.Text))
                        .Select(w => new DepthText(w.Text.Trim(), w.Depth))
                        .ToList();

            if (words.Count == 0)
            {
                return(null);
            }

            var rootFullName      = !string.IsNullOrEmpty(outerName) ? outerName + "." + words[0].Text : words[0].Text;
            var rightBracketRegex = new Regex("^\\s*\\]\\s*$");
            var rootType          = new TypeInfo.Mutable(rootFullName);
            var rootDepth         = words[0].Depth;

            for (var i = 1; i < words.Count; i++)
            {
                var name  = words[i].Text;
                var depth = words[i].Depth;

                if (rightBracketRegex.IsMatch(name))
                {
                    // Gets a type whose depth is the same as an array descriptor
                    var arrayType = GetLastTypeWithDepth(rootType, depth - rootDepth);
                    arrayType.ArrayDimension++;
                }
                else
                {
                    // Gets a parent type, whose depth is the same as this depth-1
                    var parentType = GetLastTypeWithDepth(rootType, depth - rootDepth - 1);
                    parentType.TypeArgs.Add(new TypeInfo.Mutable(name));
                }
            }

            return(rootType.ToImmutable());
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Gets a <see cref="TypeInfo.Mutable"/> with the same depth as argument.
        /// If more than one type argument with the same depth is included, returns a last type argument.
        /// </summary>
        /// <param name="rootType"><see cref="TypeInfo.Mutable"/></param>
        /// <param name="depth">Target depth</param>
        /// <returns><see cref="TypeInfo"/> with the same depth as argument</returns>
        private static TypeInfo.Mutable GetLastTypeWithDepth(TypeInfo.Mutable rootType, int depth)
        {
            var type = rootType;

            for (var j = 0; j < depth; j++)
            {
                // If an input arg is correct format, this statement is not passed.
                if (rootType.TypeArgs.LastOrDefault() == null)
                {
                    break;
                }

                type = type.TypeArgs.Last();
            }

            return(type);
        }