コード例 #1
0
        public bool MoveNext()
        {
            if (_source.IsEmpty)
            {
                _current = default;
                return(false);
            }

            var state      = State.Start;
            var savedRune  = default(RuneCategory);
            var savedIndex = 0;

            var         handleFormatExtend = true;
            const State BreakMask          = State.BreakConsumeLast | State.BreakConsumeNone;
            const State StateMask          = ~BreakMask;

            var previousZwt  = _currentRune.Category == RuneWordCategory.Zwj;
            var currentRune  = _currentRune;
            var currentIndex = 0;

            while (currentIndex < _source.Length)
            {
                if (currentRune.Category == RuneWordCategory.None)
                {
                    currentRune = DecodeRune(_source, currentIndex);
                }

                _currentRune = default;

                if (state != State.Start)
                {
                    if (currentRune.Category == RuneWordCategory.Extend ||
                        currentRune.Category == RuneWordCategory.Format ||
                        currentRune.Category == RuneWordCategory.Zwj)
                    {
                        handleFormatExtend = false;
                        goto Continue;
                    }
                }

                if (previousZwt && RuneInfo.IsEmoji(currentRune.Rune))
                {
                    state = State.Emoji;
                    goto Continue;
                }

                state = state switch
                {
                    State.Start => currentRune.Category switch
                    {
                        RuneWordCategory.ALetter => State.AHLetter,
                        RuneWordCategory.HLetter => State.HLetter,
                        RuneWordCategory.Numeric => State.Numeric,
                        RuneWordCategory.Katakana => State.Katakana,
                        RuneWordCategory.ExtendNumLet => State.ExtendNumLet,
                        RuneWordCategory.RegionalIndicator => State.RegionalIndicatorHalf,
                        RuneWordCategory.Zwj => State.Zwj,
                        RuneWordCategory.WSegSpace => State.WSegSpace,
                        RuneWordCategory.Cr => HandleStartCr(ref this),
                        RuneWordCategory.Lf => State.BreakConsumeLast,
                        RuneWordCategory.Newline => State.BreakConsumeLast,
                        _ => HandleStart(ref this)
                    },
コード例 #2
0
 internal WordBoundaryEnumerator(ReadOnlySpan <char> source)
 {
     _source      = source;
     _current     = default;
     _currentRune = default;
 }