Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/regex/20.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用Python从标记中提取URL和锚文本_Python_Regex_Markdown - Fatal编程技术网

使用Python从标记中提取URL和锚文本

使用Python从标记中提取URL和锚文本,python,regex,markdown,Python,Regex,Markdown,我正在尝试从标记中提取锚文本和相关URL。我看到了这个问题。不幸的是,这个问题似乎没有完全回答我的问题 在标记中,有两种插入链接的方法: 例1: 例2: 我的脚本如下所示(请注意,我正在使用,而不是重新使用): 我的预期产出是: ('inline link', 'http://google.com') ('non inline link', 'http://yahoo.com') 如何从标记中正确捕获锚文本 如何从标记中正确捕获锚文本 将其解析为结构化格式(例如html),然后使用适当的工

我正在尝试从标记中提取锚文本和相关URL。我看到了这个问题。不幸的是,这个问题似乎没有完全回答我的问题

在标记中,有两种插入链接的方法:

例1: 例2:
我的脚本如下所示(请注意,我正在使用,而不是重新使用):

我的预期产出是:

('inline link', 'http://google.com')
('non inline link', 'http://yahoo.com')

如何从标记中正确捕获锚文本

如何从标记中正确捕获锚文本

将其解析为结构化格式(例如html),然后使用适当的工具提取链接标签和地址

import markdown
from lxml import etree

body_markdown = "This is an [inline link](http://google.com). This is a [non inline link][1]\r\n\r\n  [1]: http://yahoo.com"

doc = etree.fromstring(markdown.markdown(body_markdown))
for link in doc.xpath('//a'):
  print link.text, link.get('href')
这让我感到:

inline link http://google.com
non inline link http://yahoo.com

另一种选择是编写您自己的标记解析器,这似乎是一个不适合集中精力的地方。

您可以通过几个简单的
re
模式来完成:

import re

INLINE_LINK_RE = re.compile(r'\[([^\]]+)\]\(([^)]+)\)')
FOOTNOTE_LINK_TEXT_RE = re.compile(r'\[([^\]]+)\]\[(\d+)\]')
FOOTNOTE_LINK_URL_RE = re.compile(r'\[(\d+)\]:\s+(\S+)')


def find_md_links(md):
    """ Return dict of links in markdown """

    links = dict(INLINE_LINK_RE.findall(md))
    footnote_links = dict(FOOTNOTE_LINK_TEXT_RE.findall(md))
    footnote_urls = dict(FOOTNOTE_LINK_URL_RE.findall(md))

    for key, value in footnote_links.iteritems():
        footnote_links[key] = footnote_urls[value]
    links.update(footnote_links)

    return links
然后你可以像这样使用它:

>>> body_markdown = """
... This is an [inline link](http://google.com).
... This is a [footnote link][1].
...
... [1]: http://yahoo.com
... """
>>> links = find_md_links(body_markdown)
>>> links
{'footnote link': 'http://yahoo.com', 'inline link': 'http://google.com'}
>>> links.values()
['http://yahoo.com', 'http://google.com']

修改@mreinhardsolution以返回所有对的列表(而不是dict)
(文本,链接)

我在python3中测试,链接如下:

[h](http://google.com) and [h](https://goog.e.com)

对于常见的标记结构,例如
这是一个[footnote link][],这将失败。\n\n[footnote link]:http://google.com/“
很有趣,谢谢@larsks指出这一点,因为在最初的问题陈述中没有说明这一点。这很容易修复,但是如果有很多特殊情况(我不太了解markdown),那么使用合适的解析器确实会更好。如果这个简单的任务是他唯一需要做的事情,那么使用它似乎会有很大的开销。它失败于
body_markdown=“””这是[foo](http://hola.com).和[bla](#hols)。[foo](http://hoo)“
。结果只有最后的
foo
链接{'foo':'http://hoo“,”bla:“#hols”}
。也许把dict改成list可以解决这个问题?@mreinhardt你能帮我吗。我认为您的解决方案可以很容易地修改,以适合我的使用re模块。提前谢谢。
inline link http://google.com
non inline link http://yahoo.com
import re

INLINE_LINK_RE = re.compile(r'\[([^\]]+)\]\(([^)]+)\)')
FOOTNOTE_LINK_TEXT_RE = re.compile(r'\[([^\]]+)\]\[(\d+)\]')
FOOTNOTE_LINK_URL_RE = re.compile(r'\[(\d+)\]:\s+(\S+)')


def find_md_links(md):
    """ Return dict of links in markdown """

    links = dict(INLINE_LINK_RE.findall(md))
    footnote_links = dict(FOOTNOTE_LINK_TEXT_RE.findall(md))
    footnote_urls = dict(FOOTNOTE_LINK_URL_RE.findall(md))

    for key, value in footnote_links.iteritems():
        footnote_links[key] = footnote_urls[value]
    links.update(footnote_links)

    return links
>>> body_markdown = """
... This is an [inline link](http://google.com).
... This is a [footnote link][1].
...
... [1]: http://yahoo.com
... """
>>> links = find_md_links(body_markdown)
>>> links
{'footnote link': 'http://yahoo.com', 'inline link': 'http://google.com'}
>>> links.values()
['http://yahoo.com', 'http://google.com']
import re
    
INLINE_LINK_RE = re.compile(r'\[([^\]]+)\]\(([^)]+)\)')
FOOTNOTE_LINK_TEXT_RE = re.compile(r'\[([^\]]+)\]\[(\d+)\]')
FOOTNOTE_LINK_URL_RE = re.compile(r'\[(\d+)\]:\s+(\S+)')


def find_md_links(md):
    """ Return dict of links in markdown """

    links = list(INLINE_LINK_RE.findall(md))
    footnote_links = dict(FOOTNOTE_LINK_TEXT_RE.findall(md))
    footnote_urls = dict(FOOTNOTE_LINK_URL_RE.findall(md))

    for key in footnote_links.keys():
        links.append((footnote_links[key], footnote_urls[footnote_links[key]]))

    return links
    
[h](http://google.com) and [h](https://goog.e.com)