Jsoup官方文檔

Jsoup官方文檔中文版

解析和遍歷一個(gè)HTML文檔

一個(gè)文檔的對象模型
  • 文檔由多個(gè)Elements和TextNodes組成 (以及其它輔助nodes:詳細(xì)可查看:nodes package tree).
  • 其繼承結(jié)構(gòu)如下:Document繼承Element繼承Node. TextNode繼承 Node.
  • 一個(gè)Element包含一個(gè)子節(jié)點(diǎn)集合囤耳,并擁有一個(gè)父Element铆隘。他們還提供了一個(gè)唯一的子元素過濾列表属拾。

輸入

解析一個(gè)HTML字符串

使用靜態(tài)Jsoup.parse(String html) 方法或 Jsoup.parse(String html, String baseUri)示例代碼:

String html = "<html><head><title>First parse</title></head>"
  + "<body><p>Parsed HTML into a doc.</p></body></html>";
Document doc = Jsoup.parse(html);

parse(String html, String baseUri) 這方法能夠?qū)⑤斎氲腍TML解析為一個(gè)新的文檔 (Document)蚣录,參數(shù) baseUri 是用來將相對 URL 轉(zhuǎn)成絕對URL,并指定從哪個(gè)網(wǎng)站獲取文檔。如這個(gè)方法不適用,你可以使用 parse(String html) 方法來解析成HTML字符串如上面的示例。.

只要解析的不是空字符串震叙,就能返回一個(gè)結(jié)構(gòu)合理的文檔,其中包含(至少) 一個(gè)head和一個(gè)body元素云头。

一旦擁有了一個(gè)Document捐友,你就可以使用Document中適當(dāng)?shù)姆椒ɑ蛩割?ElementNode中的方法來取得相關(guān)數(shù)據(jù)。

解析一個(gè)body片斷

使用Jsoup.parseBodyFragment(String html)方法.

String html = "<div><p>Lorem ipsum.</p>";
Document doc = Jsoup.parseBodyFragment(html);
Element body = doc.body();

parseBodyFragment 方法創(chuàng)建一個(gè)空殼的文檔溃槐,并插入解析過的HTML到body元素中匣砖。假如你使用正常的 Jsoup.parse(String html) 方法,通常你也可以得到相同的結(jié)果昏滴,但是明確將用戶輸入作為 body片段處理猴鲫,以確保用戶所提供的任何糟糕的HTML都將被解析成body元素。

Document.body() 方法能夠取得文檔body元素的所有子元素谣殊,與 doc.getElementsByTag("body")相同拂共。

從一個(gè)URL加載一個(gè)Document

使用 Jsoup.connect(String url)方法:

Document doc = Jsoup.connect("http://example.com/").get();
String title = doc.title();

connect(String url) 方法創(chuàng)建一個(gè)新的 Connection, 和 get() 取得和解析一個(gè)HTML文件。如果從該URL獲取HTML時(shí)發(fā)生錯誤姻几,便會拋出 IOException宜狐,應(yīng)適當(dāng)處理。

Connection 接口還提供一個(gè)方法鏈來解決特殊請求蛇捌,具體如下:

Document doc = Jsoup.connect("http://example.com")
  .data("query", "Java")
  .userAgent("Mozilla")
  .cookie("auth", "token")
  .timeout(3000)
  .post();

這個(gè)方法只支持Web URLs (httphttps 協(xié)議); 假如你需要從一個(gè)文件加載抚恒,可以使用 parse(File in, String charsetName) 代替。

從一個(gè)文件加載一個(gè)文檔

可以使用靜態(tài) Jsoup.parse(File in, String charsetName, String baseUri) 方法:

File input = new File("/tmp/input.html");
Document doc = Jsoup.parse(input, "UTF-8", "http://example.com/");

parse(File in, String charsetName, String baseUri) 這個(gè)方法用來加載和解析一個(gè)HTML文件络拌。如在加載文件的時(shí)候發(fā)生錯誤俭驮,將拋出IOException,應(yīng)作適當(dāng)處理春贸。

baseUri 參數(shù)用于解決文件中URLs是相對路徑的問題混萝。如果不需要可以傳入一個(gè)空的字符串。

另外還有一個(gè)方法parse(File in, String charsetName) 萍恕,它使用文件的路徑做為 baseUri逸嘀。 這個(gè)方法適用于如果被解析文件位于網(wǎng)站的本地文件系統(tǒng),且相關(guān)鏈接也指向該文件系統(tǒng)允粤。

解析

使用DOM方法來遍歷一個(gè)文檔

將HTML解析成一個(gè)Document之后厘熟,就可以使用類似于DOM的方法進(jìn)行操作屯蹦。示例代碼:

File input = new File("/tmp/input.html");
Document doc = Jsoup.parse(input, "UTF-8", "http://example.com/");

Element content = doc.getElementById("content");
Elements links = content.getElementsByTag("a");
for (Element link : links) {
  String linkHref = link.attr("href");
  String linkText = link.text();
}

說明

Elements這個(gè)對象提供了一系列類似于DOM的方法來查找元素,抽取并處理其中的數(shù)據(jù)绳姨。具體如下:

查找元素

  • getElementById(String id)
  • getElementsByTag(String tag)
  • getElementsByClass(String className)
  • getElementsByAttribute(String key) (and related methods)
  • Element siblings: siblingElements(), firstElementSibling(), lastElementSibling();nextElementSibling(), previousElementSibling()
  • Graph: parent(), children(), child(int index)

元素?cái)?shù)據(jù)

  • attr(String key)獲取屬性attr(String key, String value)設(shè)置屬性
  • attributes()獲取所有屬性
  • id(), className() and classNames()
  • text()獲取文本內(nèi)容text(String value) 設(shè)置文本內(nèi)容
  • html()獲取元素內(nèi)HTMLhtml(String value)設(shè)置元素內(nèi)的HTML內(nèi)容
  • outerHtml()獲取元素外HTML內(nèi)容
  • data()獲取數(shù)據(jù)內(nèi)容(例如:script和style標(biāo)簽)
  • tag() and tagName()

操作HTML和文本

  • append(String html), prepend(String html)
  • appendText(String text), prependText(String text)
  • appendElement(String tagName), prependElement(String tagName)
  • html(String value)

使用選擇器語法來查找元素

可以使用Element.select(String selector)Elements.select(String selector) 方法實(shí)現(xiàn):

File input = new File("/tmp/input.html");
Document doc = Jsoup.parse(input, "UTF-8", "http://example.com/");

Elements links = doc.select("a[href]"); //帶有href屬性的a元素
Elements pngs = doc.select("img[src$=.png]");
  //擴(kuò)展名為.png的圖片

Element masthead = doc.select("div.masthead").first();
  //class等于masthead的div標(biāo)簽

Elements resultLinks = doc.select("h3.r > a"); //在h3元素之后的a元素

說明

jsoup elements對象支持類似于CSS (或jquery)的選擇器語法,來實(shí)現(xiàn)非常強(qiáng)大和靈活的查找功能阔挠。.

這個(gè)select 方法在Document, Element,或Elements對象中都可以使用飘庄。且是上下文相關(guān)的,因此可實(shí)現(xiàn)指定元素的過濾购撼,或者鏈?zhǔn)竭x擇訪問跪削。
Select方法將返回一個(gè)Elements集合,并提供一組方法來抽取和處理結(jié)果迂求。

Selector選擇器概述

  • tagname: 通過標(biāo)簽查找元素碾盐,比如:a
  • ns|tag: 通過標(biāo)簽在命名空間查找元素,比如:可以用 fb|name 語法來查找 <fb:name> 元素
  • #id: 通過ID查找元素揩局,比如:#logo
  • .class: 通過class名稱查找元素毫玖,比如:.masthead
  • [attribute]: 利用屬性查找元素,比如:[href]
  • [^attr]: 利用屬性名前綴來查找元素凌盯,比如:可以用[^data-] 來查找?guī)в蠬TML5 Dataset屬性的元素
  • [attr=value]: 利用屬性值來查找元素付枫,比如:[width=500]
  • [attr^=value], [attr$=value], [attr*=value]: 利用匹配屬性值開頭、結(jié)尾或包含屬性值來查找元素驰怎,比如:[href*=/path/]
  • [attr~=regex]: 利用屬性值匹配正則表達(dá)式來查找元素阐滩,比如: img[src~=(?i)\.(png|jpe?g)]
  • *: 這個(gè)符號將匹配所有元素

Selector選擇器組合使用

  • el#id: 元素+ID,比如: div#logo
  • el.class: 元素+class县忌,比如: div.masthead
  • el[attr]: 元素+class掂榔,比如: a[href]
  • 任意組合,比如:a[href].highlight
  • ancestor child: 查找某個(gè)元素下子元素症杏,比如:可以用.body p 查找在"body"元素下的所有 p元素
  • parent > child: 查找某個(gè)父元素下的直接子元素装获,比如:可以用div.content > p 查找 p 元素,也可以用body > * 查找body標(biāo)簽下所有直接子元素
  • siblingA + siblingB: 查找在A元素之前第一個(gè)同級元素B鸳慈,比如:div.head + div
  • siblingA ~ siblingX: 查找A元素之前的同級X元素饱溢,比如:h1 ~ p
  • el, el, el:多個(gè)選擇器組合,查找匹配任一選擇器的唯一元素走芋,例如:div.masthead, div.logo

偽選擇器selectors

  • :lt(n): 查找哪些元素的同級索引值(它的位置在DOM樹中是相對于它的父節(jié)點(diǎn))小于n绩郎,比如:td:lt(3) 表示小于三列的元素
  • :gt(n):查找哪些元素的同級索引值大于n``,比如div p:gt(2)表示哪些div中有包含2個(gè)以上的p元素
  • :eq(n): 查找哪些元素的同級索引值與n相等翁逞,比如:form input:eq(1)表示包含一個(gè)input標(biāo)簽的Form元素
  • :has(seletor): 查找匹配選擇器包含元素的元素肋杖,比如:div:has(p)表示哪些div包含了p元素
  • :not(selector): 查找與選擇器不匹配的元素,比如: div:not(.logo) 表示不包含 class=logo 元素的所有 div 列表
  • :contains(text): 查找包含給定文本的元素挖函,搜索不區(qū)分大不寫状植,比如: p:contains(jsoup)
  • :containsOwn(text): 查找直接包含給定文本的元素
  • :matches(regex): 查找哪些元素的文本匹配指定的正則表達(dá)式,比如:div:matches((?i)login)
  • :matchesOwn(regex): 查找自身包含文本匹配指定正則表達(dá)式的元素
  • 注意:上述偽選擇器索引是從0開始的,也就是說第一個(gè)元素索引值為0津畸,第二個(gè)元素index為1等

從元素抽取屬性振定,文本和HTML

方法
  • 要取得一個(gè)屬性的值,可以使用Node.attr(String key) 方法
  • 對于一個(gè)元素中的文本肉拓,可以使用Element.text()方法
  • 對于要取得元素或?qū)傩灾械腍TML內(nèi)容后频,可以使用Element.html(), 或 Node.outerHtml()方法

示例:

String html = "<p>An <a ><b>example</b></a> link.</p>";
Document doc = Jsoup.parse(html);//解析HTML字符串返回一個(gè)Document實(shí)現(xiàn)
Element link = doc.select("a").first();//查找第一個(gè)a元素

String text = doc.body().text(); // "An example link"http://取得字符串中的文本
String linkHref = link.attr("href"); // "http://example.com/"http://取得鏈接地址
String linkText = link.text(); // "example""http://取得鏈接地址中的文本

String linkOuterH = link.outerHtml(); 
    // "<a 
String linkInnerH = link.html(); // "<b>example</b>"http://取得鏈接內(nèi)的html內(nèi)容

說明

上述方法是元素?cái)?shù)據(jù)訪問的核心辦法。此外還其它一些方法可以使用:

  • Element.id()
  • Element.tagName()
  • Element.className() and Element.hasClass(String className)

這些訪問器方法都有相應(yīng)的setter方法來更改數(shù)據(jù).

處理URLs

問題

你有一個(gè)包含相對URLs路徑的HTML文檔暖途,需要將這些相對路徑轉(zhuǎn)換成絕對路徑的URLs卑惜。

方法
  1. 在你解析文檔時(shí)確保有指定base URI,然后
  2. 使用 abs: 屬性前綴來取得包含base URI的絕對路徑驻售。代碼如下:
Document doc = Jsoup.connect("http://www.open-open.com").get();

Element link = doc.select("a").first();
String relHref = link.attr("href"); // == "/"
String absHref = link.attr("abs:href"); // "http://www.open-open.com/"

說明

在HTML元素中露久,URLs經(jīng)常寫成相對于文檔位置的相對路徑: <a href="/download">...</a>. 當(dāng)你使用 Node.attr(String key) 方法來取得a元素的href屬性時(shí),它將直接返回在HTML源碼中指定定的值欺栗。

假如你需要取得一個(gè)絕對路徑毫痕,需要在屬性名前加 abs: 前綴。這樣就可以返回包含根路徑的URL地址attr("abs:href")

因此纸巷,在解析HTML文檔時(shí)镇草,定義base URI非常重要。

如果你不想使用abs: 前綴瘤旨,還有一個(gè)方法能夠?qū)崿F(xiàn)同樣的功能 Node.absUrl(String key)梯啤。

數(shù)據(jù)修改

設(shè)置屬性的值

問題

在你解析一個(gè)Document之后可能想修改其中的某些屬性值,然后再保存到磁盤或都輸出到前臺頁面存哲。

方法

可以使用屬性設(shè)置方法 Element.attr(String key, String value), 和 Elements.attr(String key, String value).

假如你需要修改一個(gè)元素的 class 屬性因宇,可以使用 Element.addClass(String className)Element.removeClass(String className) 方法。

Elements 提供了批量操作元素屬性和class的方法祟偷,比如:要為div中的每一個(gè)a元素都添加一個(gè)rel="nofollow" 可以使用如下方法:

doc.select("div.comments a").attr("rel", "nofollow");

說明

Element中的其它方法一樣察滑,attr 方法也是返回當(dāng)前 Element (或在使用選擇器是返回 Elements 集合)。這樣能夠很方便使用方法連用的書寫方式修肠。比如:

doc.select("div.masthead").attr("title", "jsoup").addClass("round-box");
設(shè)置一個(gè)元素的HTML內(nèi)容
方法

可以使用Element中的HTML設(shè)置方法具體如下:

Element div = doc.select("div").first(); // <div></div>
div.html("<p>lorem ipsum</p>"); // <div><p>lorem ipsum</p></div>
div.prepend("<p>First</p>");//在div前添加html內(nèi)容
div.append("<p>Last</p>");//在div之后添加html內(nèi)容
// 添完后的結(jié)果: <div><p>First</p><p>lorem ipsum</p><p>Last</p></div>

Element span = doc.select("span").first(); // <span>One</span>
span.wrap("<li><a );
// 添完后的結(jié)果: <li><a ><span>One</span></a></li>

說明
  • Element.html(String html) 這個(gè)方法將先清除元素中的HTML內(nèi)容贺辰,然后用傳入的HTML代替。
  • Element.prepend(String first)Element.append(String last) 方法用于在分別在元素內(nèi)部HTML的前面和后面添加HTML內(nèi)容
  • Element.wrap(String around) 對元素包裹一個(gè)外部HTML內(nèi)容嵌施。
設(shè)置元素的文本內(nèi)容
方法

可以使用Element的設(shè)置方法:

Element div = doc.select("div").first(); // <div></div>
div.text("five > four"); // <div>five &gt; four</div>
div.prepend("First ");
div.append(" Last");
// now: <div>First five &gt; four Last</div>
說明

文本設(shè)置方法與 HTML setter方法一樣:

  • Element.text(String text) 將清除一個(gè)元素中的內(nèi)部HTML內(nèi)容饲化,然后提供的文本進(jìn)行代替
  • Element.prepend(String first)Element.append(String last) 將分別在元素的內(nèi)部html前后添加文本節(jié)點(diǎn)晃洒。

對于傳入的文本如果含有像 <, > 等這樣的字符木人,將以文本處理婚肆,而非HTML擎勘。

消除不受信任的HTML (來防止XSS攻擊)

問題

在做網(wǎng)站的時(shí)候,經(jīng)常會提供用戶評論的功能遇绞。有些不懷好意的用戶暇韧,會搞一些腳本到評論內(nèi)容中护桦,而這些腳本可能會破壞整個(gè)頁面的行為,更嚴(yán)重的是獲取一些機(jī)要信息族奢,此時(shí)需要清理該HTML姥闭,以避免跨站腳本cross-site scripting攻擊(XSS)。

方法

使用jsoup HTML Cleaner 方法進(jìn)行清除歹鱼,但需要指定一個(gè)可配置的 Whitelist

String unsafe = 
  "<p><a  onclick='stealCookies()'>Link</a></p>";
String safe = Jsoup.clean(unsafe, Whitelist.basic());
// now: <p><a  rel="nofollow">Link</a></p>

說明

XSS又叫CSS (Cross Site Script) 泣栈,跨站腳本攻擊。它指的是惡意攻擊者往Web頁面里插入惡意html代碼弥姻,當(dāng)用戶瀏覽該頁之時(shí),嵌入其中Web里面的html代碼會被執(zhí)行掺涛,從而達(dá)到惡意攻擊用戶的特殊目的庭敦。XSS屬于被動式的攻擊,因?yàn)槠浔粍忧也缓美眯嚼拢栽S多人常忽略其危害性秧廉。所以我們經(jīng)常只讓用戶輸入純文本的內(nèi)容,但這樣用戶體驗(yàn)就比較差了拣帽。

一個(gè)更好的解決方法就是使用一個(gè)富文本編輯器WYSIWYG如CKEditorTinyMCE疼电。這些可以輸出HTML并能夠讓用戶可視化編輯。雖然他們可以在客戶端進(jìn)行校驗(yàn)减拭,但是這樣還不夠安全蔽豺,需要在服務(wù)器端進(jìn)行校驗(yàn)并清除有害的HTML代碼,這樣才能確保輸入到你網(wǎng)站的HTML是安全的拧粪。否則修陡,攻擊者能夠繞過客戶端的Javascript驗(yàn)證,并注入不安全的HMTL直接進(jìn)入您的網(wǎng)站可霎。

jsoup的whitelist清理器能夠在服務(wù)器端對用戶輸入的HTML進(jìn)行過濾魄鸦,只輸出一些安全的標(biāo)簽和屬性。

jsoup提供了一系列的Whitelist基本配置癣朗,能夠滿足大多數(shù)要求拾因;但如有必要,也可以進(jìn)行修改旷余,不過要小心绢记。

這個(gè)cleaner非常好用不僅可以避免XSS攻擊,還可以限制用戶可以輸入的標(biāo)簽范圍荣暮。

參見
  • 參閱XSS cheat sheet 庭惜,有一個(gè)例子可以了解為什么不能使用正則表達(dá)式,而采用安全的whitelist parser-based清理器才是正確的選擇穗酥。
  • 參閱Cleaner护赊,了解如何返回一個(gè) Document 對象惠遏,而不是字符串
  • 參閱Whitelist,了解如何創(chuàng)建一個(gè)自定義的whitelist
  • nofollow 鏈接屬性了解
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末骏啰,一起剝皮案震驚了整個(gè)濱河市节吮,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌判耕,老刑警劉巖透绩,帶你破解...
    沈念sama閱讀 212,816評論 6 492
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異壁熄,居然都是意外死亡帚豪,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,729評論 3 385
  • 文/潘曉璐 我一進(jìn)店門草丧,熙熙樓的掌柜王于貴愁眉苦臉地迎上來狸臣,“玉大人,你說我怎么就攤上這事昌执≈蛞啵” “怎么了?”我有些...
    開封第一講書人閱讀 158,300評論 0 348
  • 文/不壞的土叔 我叫張陵懂拾,是天一觀的道長煤禽。 經(jīng)常有香客問我,道長岖赋,這世上最難降的妖魔是什么檬果? 我笑而不...
    開封第一講書人閱讀 56,780評論 1 285
  • 正文 為了忘掉前任,我火速辦了婚禮贾节,結(jié)果婚禮上汁汗,老公的妹妹穿的比我還像新娘。我一直安慰自己栗涂,他們只是感情好知牌,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,890評論 6 385
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著斤程,像睡著了一般角寸。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上忿墅,一...
    開封第一講書人閱讀 50,084評論 1 291
  • 那天扁藕,我揣著相機(jī)與錄音,去河邊找鬼疚脐。 笑死亿柑,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的棍弄。 我是一名探鬼主播望薄,決...
    沈念sama閱讀 39,151評論 3 410
  • 文/蒼蘭香墨 我猛地睜開眼疟游,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了痕支?” 一聲冷哼從身側(cè)響起颁虐,我...
    開封第一講書人閱讀 37,912評論 0 268
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎卧须,沒想到半個(gè)月后另绩,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 44,355評論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡花嘶,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,666評論 2 327
  • 正文 我和宋清朗相戀三年笋籽,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片椭员。...
    茶點(diǎn)故事閱讀 38,809評論 1 341
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡干签,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出拆撼,到底是詐尸還是另有隱情,我是刑警寧澤喘沿,帶...
    沈念sama閱讀 34,504評論 4 334
  • 正文 年R本政府宣布闸度,位于F島的核電站,受9級特大地震影響蚜印,放射性物質(zhì)發(fā)生泄漏莺禁。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 40,150評論 3 317
  • 文/蒙蒙 一窄赋、第九天 我趴在偏房一處隱蔽的房頂上張望哟冬。 院中可真熱鬧,春花似錦忆绰、人聲如沸浩峡。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,882評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽翰灾。三九已至,卻和暖如春稚茅,著一層夾襖步出監(jiān)牢的瞬間纸淮,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,121評論 1 267
  • 我被黑心中介騙來泰國打工亚享, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留咽块,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 46,628評論 2 362
  • 正文 我出身青樓欺税,卻偏偏與公主長得像侈沪,于是被迫代替她去往敵國和親揭璃。 傳聞我的和親對象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,724評論 2 351

推薦閱讀更多精彩內(nèi)容

  • 問答題47 /72 常見瀏覽器兼容性問題與解決方案峭竣? 參考答案 (1)瀏覽器兼容問題一:不同瀏覽器的標(biāo)簽?zāi)J(rèn)的外補(bǔ)...
    _Yfling閱讀 13,742評論 1 92
  • 第一部分 HTML&CSS整理答案 1. 什么是HTML5塘辅? 答:HTML5是最新的HTML標(biāo)準(zhǔn)。 注意:講述HT...
    kismetajun閱讀 27,453評論 1 45
  • 學(xué)會蛙泳已經(jīng)有很多年了呻惕,可是仰泳卻怎么也學(xué)不會,我想今年把仰泳學(xué)會滥比,所以練習(xí)仰泳成了我今年游泳的目標(biāo)亚脆。 昨天游完兩...
    ailsa寧波閱讀 149評論 0 1
  • 1.放大/縮小字體:ctrl[/] 2.日期shift alt D 3.時(shí)間shift alt T 4.雙擊格式刷...
    臉大大閱讀 156評論 0 0