Java 将嵌套的项目符号列表文本转换为HTML

Java 将嵌套的项目符号列表文本转换为HTML,java,html,text-to-html,Java,Html,Text To Html,我有这个: 输入示例: * First item * Second item * Subitem 1 * sub-subitem! * Subitem 3 * Third item 示例输出: <ul> <li>First item</li> <li>Second item <ul> <li>Subitem 1

我有这个: 输入示例:

* First item
* Second item
    * Subitem 1
        * sub-subitem!
    * Subitem 3
* Third item
示例输出:

<ul>
    <li>First item</li>
    <li>Second item
        <ul>
            <li>Subitem 1
                <ul>
                    <li>sub-subitem!</li>
                </ul>
            </li>
            <li>Subitem 3</li>
        </ul>
    </li>
    <li>Third item</li>
</ul>
  • 第一项
  • 第二项
    • 分项1
      • 分项!
    • 分项3
  • 第三项
我创建了一个Java类,它将每一个字符串行发送到一个字符数组,并单独处理每个字符。 我的问题是何时关闭标签 有什么想法吗

这是我的密码:

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;

public class TextToHtml {
    StringBuilder itemName = new StringBuilder();
    String sCurrentLine;
    int usingUlTAG=0;

public TextToHtml(){
        BufferedReader br = null; 
        try {
            boolean closeLItag=false;
            br = new BufferedReader(new FileReader("NestedText.txt"));
            System.out.println("<ul>");
            while ((sCurrentLine = br.readLine()) != null) {
                    char[] item = sCurrentLine.toCharArray();
                    for(int i=0; i<item.length;i++){
                            if(item[i]!='*' && item[i]!='\n' && item[i]!='\t'){
                                    itemName.append(item[i]); 
                continue;
            }   
            if(item[i]=='*'){   
                itemName.append("<li>");
                closeLItag=true;
            }
            else if(item[i]=='\t'){ 
                if(item[i+1]=='*'){ 
                    if(usingUlTAG<1)
                    itemName.append("\t<ul>\n\t\t");
                    itemName.append("\t\n\t\t");
                    usingUlTAG= 1;
                    continue;
                }
                if(item[i+1]=='\t'){    
                    itemName.append("\t\t<ul>\n\n\t\t");
                    usingUlTAG=2;
                    continue;
                }
            }
        }
        if(closeLItag){
            itemName.append("</li>\n");
        }

    }       
    System.out.println(itemName+"/ul>");
    } catch (IOException e) {
        e.printStackTrace();
    } finally {
        try {
            if (br != null)br.close();
        } catch (IOException ex) {
            ex.printStackTrace();
        }
    }
}

public static void main(String[] args) {
    new TextToHtml();   
}
}
导入java.io.BufferedReader;
导入java.io.FileReader;
导入java.io.IOException;
公共类TextToHtml{
StringBuilder itemName=新建StringBuilder();
弦电流线;
int usingUlTAG=0;
public TextToHtml(){
BufferedReader br=null;
试一试{
布尔closeLItag=false;
br=新的BufferedReader(新的文件读取器(“NestedText.txt”);
System.out.println(“
    ”); 而((sCurrentLine=br.readLine())!=null){ char[]item=sCurrentLine.toCharArray();
    对于(int i=0;i,您必须向前看下一行,看看它的列表级别是否与当前项目的不同。然后,您可以根据级别的差异添加或关闭标记(如果有)。下面是执行此操作的代码:

    import java.io.BufferedReader;
    import java.io.FileReader;
    import java.io.IOException;
    
    public class TextToHtml
    {
        StringBuilder itemName = new StringBuilder();
        String sCurrentLine;
        String sNextLine; // A "peek" at what's next to determine if </li> is needed
    
        public TextToHtml()
        {
            BufferedReader br = null;
            try
            {
                br = new BufferedReader(new FileReader("NestedText.txt"));
                System.out.println("<ul>");
                sNextLine = br.readLine();
                while ((sCurrentLine = sNextLine) != null)
                {
                    sNextLine = br.readLine();
    
                    char[] item = sCurrentLine.toCharArray();
                    int itemLevel = 0;
                    for (int i = 0; i < item.length; i++)
                    {
                        if (item[i] != '*' && item[i] != '\n' && item[i] != '\t')
                        {
                            itemName.append(item[i]);
                        }
                        else if (item[i] == '*')
                        {
                            itemName.append("\t<li>");
    
                            // Trim leading space character
                            if (item[i + 1] == ' ')
                                i++;
                        }
                        else if (item[i] == '\t')
                        {
                            itemLevel++;
                            itemName.append("\t\t");
                        }
                    }
    
                    int nextItemLevel = 0;
                    if (sNextLine != null)
                    {
                        char[] nextItem = sNextLine.toCharArray();
                        for (int i = 0; i < nextItem.length; i++)
                        {
                            if (nextItem[i] == '\t')
                                nextItemLevel++;
                            else
                                break;
                        }
                    }
                    // Next is the same level; there are no subitems
                    if (itemLevel == nextItemLevel)
                        itemName.append("</li>");
                    // Next is a deeper level; there are subitems
                    else if (itemLevel < nextItemLevel)
                    {
                        // In case the next item is more than 1 level deeper
                        for (int i = itemLevel + 1; i <= nextItemLevel; i++)
                        {
                            itemName.append("\n");
                            for (int j = 0; j < i; j++)
                                itemName.append("\t\t");
                            itemName.append("<ul>");
    
                            // If the next item's level is reached, it will create its own     <li>
                            if (i != nextItemLevel)
                            {
                                itemName.append("\n");
                                for (int j = 0; j < i; j++)
                                    itemName.append("\t\t");
                                itemName.append("\t<li>");
                            }
                        }
                    }
                    // Next is a higher level; there are tags to close
                    else // (itemLevel > nextItemLevel)
                    {
                        itemName.append("</li>");
                        for (int i = itemLevel - 1; i >= nextItemLevel; i--)
                        {
                            itemName.append("\n");
                            for (int j = 0; j <= i; j++)
                                itemName.append("\t\t");
                            itemName.append("</ul>\n");
                            for (int j = 0; j < i; j++)
                                itemName.append("\t\t");
                            itemName.append("\t</li>");
                        }
                    }
                    itemName.append("\n");
                }
                System.out.println(itemName + "</ul>");
            }
            catch (IOException e)
            {
                e.printStackTrace();
            }
            finally
            {
                try
                {
                    if (br != null)
                        br.close();
                }
                catch (IOException ex)
                {
                    ex.printStackTrace();
                }
            }
        }
    
        public static void main(String[] args)
        {
            new TextToHtml();
        }
    }
    
    导入java.io.BufferedReader;
    导入java.io.FileReader;
    导入java.io.IOException;
    公共类TextToHtml
    {
    StringBuilder itemName=新建StringBuilder();
    弦电流线;
    String sNextLine;//查看下一步内容以确定是否需要
    public TextToHtml()
    {
    BufferedReader br=null;
    尝试
    {
    br=新的BufferedReader(新的文件读取器(“NestedText.txt”);
    System.out.println(“
      ”); sNextLine=br.readLine(); 而((sCurrentLine=sNextLine)!=null) { sNextLine=br.readLine(); char[]item=sCurrentLine.toCharArray(); int itemLevel=0; 对于(int i=0;i”); //修剪前导空格字符 如果(项目[i+1]='') i++; } 否则如果(项目[i]='\t') { itemLevel++; itemName.append(“\t\t”); } } int nextItemLevel=0; 如果(sNextLine!=null) { char[]nextItem=sNextLine.toCharArray(); 对于(int i=0;i”); //接下来是一个更深的层次;有子项 else if(itemLevel对于(int i=itemLevel+1;i如果如您当前的代码所示,原始文本中的列表项行都使用硬制表符进行缩进,那么您需要做的就是一次一行地处理文本,跟踪缩进级别(制表符数)这段代码不会在生成的HTML中产生很好的缩进,但是它得到了HTML浏览器真正关心的
      • 嵌套

        import java.io.*;
        import java.util.regex.*;
        
        public class Main {
          public static void main(String[] args) throws Exception {
            StringBuilder result = new StringBuilder();
            BufferedReader br = new BufferedReader(new FileReader("NestedText.txt"));
            try {
              int lastIndent = -1; // indent level of last line
              int depth = 0; // number of levels of <ul> we are currently inside
              String line;
              Pattern indentPattern = Pattern.compile("((\\t*)\\* )?(.*)");
              while((line = br.readLine()) != null) {
                Matcher m = indentPattern.matcher(line);
                m.matches(); // guaranteed to be true, but needed to update matcher state
        
                if(m.group(1) != null) { // this is a new list item
                  int thisIndent = m.end(2); // number of leading tabs, may be zero
        
                  // there are three possible cases
                  if(thisIndent == lastIndent) {
                    // same level as last list item
                    result.append("</li>");
                  } else if(thisIndent > lastIndent) {
                    // starting a child list
                    result.append("<ul>");
                    depth++;
                  } else {
                    // returning to parent list
                    result.append("</li>");
                    depth--;
                    result.append("</ul>");
                    result.append("</li>");
                  }
        
                  result.append("<li>");
                  lastIndent = thisIndent;
                } else { // this is a continuation of the previous list item
                  result.append(" ");
                }
                // append this line's text (not including the indent and *)
                result.append(m.group(3));
              }
        
              // run out of items, close any outstanding lists
              while(depth-- > 0) {
                result.append("</li>");
                result.append("</ul>");
              }
        
              System.out.println(result);
            } finally {
              br.close();
            }
          }
        }
        

        没问题。

        根据Jan Dvorak的建议,我已经解决了这个问题。 以下代码适用于,我将在下面列出,以防它对其他人有所帮助。 谢谢你的贡献

        MarkdownProcessor m = new MarkdownProcessor(); 
        String html = null;
        try {
        html = m.markdown(MyString));
        } catch (IOException e) {
        e.printStackTrace();
        } 
        System.out.println(html);
        

        您可以通过编程方式在内存中生成DOM树,然后让标准库代码为您将其写入字符串。不必再担心标记的关闭。标记确实如此,这就是每行开头保证的“*”?如果是这样,您可能可以将其剥离,并通过查找换行来决定新项目的开始时间。是的,“*”不知何故,他是一个必须的markerHi-Ian,谢谢你的回答