zoukankan      html  css  js  c++  java
  • Razor潜入2令人疑惑的LocateOwner方法

           我们知道页面引擎尤其是Razor的核心是如何对页面上的代码的解析。

    而其中的核心的是一个语法解析树中的定位应该改变也算是非常频繁的操作。

    对于其中关键的LocateOwner函数真的令我疑惑。

    简单说明一下Razor中的语法树。Razor源码中是这样定义的。

    image

    基本机构,由上图可以知道。

    Block就是一个集合,可以看成是一篇文章或一个句子,span就是具体表达的一个小块。

    其中Block 提供了一个为'变动'提供定位span的方法。

    /// <summary> 
          
    /// 定位改变所属的 块 
          
    /// </summary> 
          
    /// <param name="change"></param> 
          
    /// <returns></returns> 
          public Span LocateOwner(TextChange change) { 
              
    // Ask each child recursively 
              Span owner = null;
              
    foreach (SyntaxTreeNode element in Children) { 
                  Span span 
    = element as Span;
                  
    if (span == null) { 
                      owner 
    = ((Block)element).LocateOwner(change);//如果是块则递归往下找 
                  } 
                  
    else { 
                      
    if (change.Position < span.Start.AbsoluteIndex) {//超出-属于span 
                          
    // Early escape for cases where changes overlap multiple spans 
                          
    // In those cases, the span will return false, and we don't want to search the whole tree 
                          
    // So if the current span starts after the change, we know we've searched as far as we need to 
                          break
                      } 
                      owner 
    = span.OwnsChange(change) ? span : owner;//deph 
                  }
                  
    if (owner != null) {//是否已经得到答案 
                      break
                  } 
              }
              
    return owner; 
          }
    //再给出span.OwnsChange(change) 的源码

    /// <summary> 
          
    /// Determines if the specified change belongs to this span. 
          
    /// </summary> 
          
    /// <remarks> 
          
    /// Used for Partial Parsing to identify which span to augment with the specified change. 
          
    /// Some changes have no owner, because they overlap multiple spans. 
          
    /// Also, just because a span owns a change, doesn't mean it can accept it 
          
    /// </remarks> 
          public virtual bool OwnsChange(TextChange change) { 
              
    int changeOldEnd = change.Position + change.OldLength; 
              
    return change.Position >= Start.AbsoluteIndex && 
                     (changeOldEnd 
    < EndIndex || (changeOldEnd == EndIndex && CanGrow)); 
          }

    这里很明显可以看到作者采用深度优先的策略,这不是很奇怪吗?为什么不采用广度优先?

    不是更容易定位吗?难道我又错了?想到半夜都没想通。大家说说看。

  • 相关阅读:
    【2018.05.05 C与C++基础】C++中的自动废料收集:概念与问题引入
    【2018.04.27 C与C++基础】关于switch-case及if-else的效率问题
    【2018.04.19 ROS机器人操作系统】机器人控制:运动规划、路径规划及轨迹规划简介之一
    March 11th, 2018 Week 11th Sunday
    March 10th, 2018 Week 10th Saturday
    March 09th, 2018 Week 10th Friday
    March 08th, 2018 Week 10th Thursday
    March 07th, 2018 Week 10th Wednesday
    ubantu之Git使用
    AMS分析 -- 启动过程
  • 原文地址:https://www.cnblogs.com/facingwaller/p/1910347.html
Copyright © 2011-2022 走看看