private void button4_Click(object sender, EventArgs e)
{
    string text = richTextBox1.Text;
    production = new Dictionary<string, List<string>>();
    string[] pro = text.Split('
');
    foreach (string s in pro)
    {
        if (s == "") continue;

        Regex.Replace(s, " ", "");
        string[] ga = Regex.Split(s, "->");
        if (ga.Length != 2) return;
        if (ga[0].Length == 0 || ga[1].Length == 0)
            return;
        if (ga[0].Length != 1 || !char.IsUpper(ga[0][0])) return;

        string[] ga2 = Regex.Split(ga[1], "|");
        if (!production.ContainsKey(ga[0]))
            production.Add(ga[0], new List<string>());
        foreach (string s1 in ga2)
            production[ga[0]].Add(s1);
    }

    firsts = new Dictionary<string, List<string>>();
    foreach (var item in production.Keys)
        GetFirst(item, production, firsts);

    follows = new Dictionary<string, List<string>>();
    foreach (var item in production.Keys)
        GetFollow(item, production, firsts, follows);


    if (JudgeLL1(production, firsts, follows))
    {
        MessageBox.Show("该文法是LL(1)文法\n");
        
    }
    else
    {
        MessageBox.Show("该文法不是LL(1)文法,存在左递归或者存在FIRST集合有交集的情况!\n");
    }
    button1.Enabled = true;
    button2.Enabled = true;
    button3.Enabled = true;
}
private void button1_Click(object sender, EventArgs e)
{
    // 获取所有的符号集合
    List<string> symbols = new List<string>();
    foreach (var item in production.Keys)
    {
        if (!symbols.Contains(item))
            symbols.Add(item);
        foreach (var prod in production[item])
        {
            foreach (var c in prod)
            {
                if (!symbols.Contains(c.ToString()))
                    symbols.Add(c.ToString());
            }
        }
    }
    // 将符号集合按照终结符和非终结符分开
    nonterminals = new List<string>();
    terminals = new List<string>();
    foreach (var s in symbols)
    {
        if (char.IsUpper(s[0]))
            nonterminals.Add(s);
        else
            terminals.Add(s);
    }
    if (terminals.IndexOf("#") == -1)
    {
        terminals.Add("#");
    }


    listView1.Columns.Clear();
    listView1.Items.Clear();
    listView1.View = View.Details;

    // 添加第一列
    listView1.Columns.Add("", 40);

    // 添加终结符列
    foreach (var item in terminals)
    {
        listView1.Columns.Add(item, 40);
    }

    // 添加非终结符行
    foreach (var item in nonterminals)
    {
        ListViewItem lvi = new ListViewItem(item);
        lvi.SubItems.Add("");
        foreach (var t in terminals)
        {
            lvi.SubItems.Add("");
        }
        listView1.Items.Add(lvi);
    }

    // 填充表格
    foreach (var item in firsts)
    {
        int row = nonterminals.IndexOf(item.Key);
        foreach (var t in terminals)
        {
            int col = terminals.IndexOf(t);
            if(!item.Value.Contains(t))
                listView1.Items[row].SubItems[col + 1].Text = "0";
            else
                listView1.Items[row].SubItems[col + 1].Text = "1";
        }
    }
}

private void button2_Click(object sender, EventArgs e)
{
    // 获取所有的符号集合
    List<string> symbols = new List<string>();
    foreach (var item in production.Keys)
    {
        if (!symbols.Contains(item))
            symbols.Add(item);
        foreach (var prod in production[item])
        {
            foreach (var c in prod)
            {
                if (!symbols.Contains(c.ToString()))
                    symbols.Add(c.ToString());
            }
        }
    }
    // 将符号集合按照终结符和非终结符分开
    nonterminals = new List<string>();
    terminals = new List<string>();
    foreach (var s in symbols)
    {
        if (char.IsUpper(s[0]))
            nonterminals.Add(s);
        else
            terminals.Add(s);
    }
    if(terminals.IndexOf("#")==-1)
    {
        terminals.Add("#");
    }

    foreach (var s in nonterminals)
    {
       System.Console.WriteLine(s);
    }

    foreach(var s in terminals)
    {
        System.Console.WriteLine(s);
    }

    listView2.Columns.Clear();
    listView2.Items.Clear();
    listView2.View = View.Details;

    // 添加第一列
    listView2.Columns.Add("", 40);

    // 添加终结符列
    foreach (var item in terminals)
    {
        listView2.Columns.Add(item, 40);
    }

    // 添加非终结符行
    foreach (var item in nonterminals)
    {
        ListViewItem lvi = new ListViewItem(item);
        lvi.SubItems.Add("");
        foreach (var t in terminals)
        {
            lvi.SubItems.Add("");
        }
        listView2.Items.Add(lvi);
    }

    // 填充表格
    foreach (var item in follows)
    {
        int row = nonterminals.IndexOf(item.Key);
        foreach (var t in terminals)
        {
            int col = terminals.IndexOf(t);
            if (!item.Value.Contains(t))
                listView2.Items[row].SubItems[col + 1].Text = "0";
            else
                listView2.Items[row].SubItems[col + 1].Text = "1";
        }
    }
}

在上述代码中加入对终结符#的判断内容:,如果终结符列表中不存在#,则添加#到终结符列表中。具体实现为:

if(terminals.IndexOf("#")==-1)
{
    terminals.Add("#");
}

这样就保证了在构建LL(1)分析表时,#这个特殊的结束符号一定会被考虑到。


原文地址: https://www.cveoy.top/t/topic/fXFw 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录