• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:文字と数字が混在する要素のsortについて)

文字と数字が混在する要素のsortについて

このQ&Aのポイント
  • 文字と数字が混在する要素のsortについて質問させていただきます。要素を時系列でsortする方法について教えてください。
  • liの中のテキストをArrayオブジェクトに代入して配列にした後、sortする方法について教えてください。文字と/など複合数字が混在している場合のソート方法を知りたいです。
  • javascript初心者です。ulタグ内のli要素を時系列で並び替えたいのですが、文字と数字が混在しているためソートできません。どのように実装すれば良いでしょうか?

質問者が選んだベストアンサー

  • ベストアンサー
  • Chaire
  • ベストアンサー率60% (79/130)
回答No.4

そもそも、HTML を使っているのに、地の文と日付データをタグで区別できていない時点で致命的です。HTML を書き換えられるなら、日付データを確実に区別しておくべきです。日付なのですから、Date オブジェクトで比較するのが確実です。 <ul>  <li>テキストを時系列で並び替えたい <span class="time">2011/05/15/19:00</span></li>  <li>テキストを時系列で並び替えたい <span class="time">2009/01/15/14:00</span></li>  <li>テキストを時系列で並び替えたい <span class="time">2010/05/15/19:00</span></li> </ul> // version(160), ("Selectors-API", "1.0"), ("Core", "3.0") Array.map (document.querySelectorAll ('ul:first-of-type > li > *.time:first-of-type'), function (time) {  // Date.parse() できる可能性の高い形式なので利用する  return { time: time, container: time.parentNode.parentNode, t: new Date (time.textContent) }; }).sort (function (o1, o2) {  return o1.t - o2.t; }).forEach (function (o) {  o.C.appendChild (o.time.parentNode); }); Date オブジェクトを作れる日付文字列は実装依存ですが、心配であれば <span title="2011/05/15 19:00"> のように機械処理可能な文字列を属性値にでも埋め込んでおけば良いでしょう。 どうしても HTML の方を修正できないのなら、日付部分を切り出します。どうせ切り出すのなら、確実に Date を作れるよう日付パラメータを切り出します。 <ul>  <li>テキストを時系列で並び替えたい 2011/05/15/19:00</li>  <li>テキストを時系列で並び替えたい 2009/01/15/14:00</li>  <li>テキストを時系列で並び替えたい 2010/05/15/19:00</li> </ul> Array.map (document.querySelectorAll ('ul:nth-of-type(2) > li'), function (li) {  var t = this.exec (li.textContent);  return { e: li, t: t ? new Date (t[1], t[2], t[3], t[4], t[5]) : NaN, L: li.parentNode }; }, /(\d{4})\/(\d{2})\/(\d{2})\/(\d{2}):(\d{2})/).sort (function (o1, o2) {  var t1 = o1.t, t2 = o2.t;  if (isNaN (t1)) return 1;  if (isNaN (t2)) return -1;  return o1.t - o2.t; }).forEach (function (o) {  o.L.appendChild (o.e); });

参考URL:
http://www.unicode.org/reports/tr10/
whosfoo
質問者

お礼

お礼が遅くなり申し訳ありません。 大変参考になりました。

その他の回答 (3)

  • think49
  • ベストアンサー率59% (285/482)
回答No.3

日時が24時間法でゼロパディングされているなら、引数なしの Array.prototype.sort() でソートできるはずです。(例示の配列はこの状態) var myArray = ['テキストを時系列で並び替えたい 2011/05/15/19:00', 'テキストを時系列で並び替えたい 2009/01/15/14:00', 'テキストを時系列で並び替えたい 2010/05/15/19:00']; myArray.sort(); alert(myArray); // ["テキストを時系列で並び替えたい 2009/01/15/14:00", "テキストを時系列で並び替えたい 2010/05/15/19:00", "テキストを時系列で並び替えたい 2011/05/15/19:00"] 日時がゼロサプレスされていると困った結果になります。 var myArray2 = ['2011/5/15/19:00', '2011/1/15/14:00', '2011/10/15/19:00']; myArray2.sort(); alert(myArray2); // ["2011/1/15/14:00", "2011/10/15/19:00", "2011/5/15/19:00"] Array#sort は文字列を先頭から1文字ずつ走査していき、アドレスの小さな順に並び替えます。 "2011/1" と "2011/5" を比較すると前者が小さいので、"2011/10/15/19:00" は "2011/5/15/19:00" より前にソートされてしまいます。 http://www2u.biglobe.ne.jp/~oz-07ams/prog/ecma262r3/15-4_Array_Objects.html#section-15.4.4.11 http://es5.github.com/#x15.4.4.11 myArray2 のパターンでソートするには「自然言語アルゴリズム」でソートする必要があります。 https://gist.github.com/660141

whosfoo
質問者

お礼

回答ありがとうございます。 お礼が遅くなりました、すみません。 今後の制作の参考にさせていただきます。

  • ssk38
  • ベストアンサー率44% (22/49)
回答No.2

> myArray.sort(function(a,b) {return a-b;}); 日時部分がうしろから16文字固定ならば、文字列比較でいけるので、 function(a,b) {return a-b;} を function(a,b){ return (a.slice(-16) > b.slice(-16)) ? 1 : -1; } に替えたらいけないですか?

whosfoo
質問者

お礼

返信ありがとうございます。 お礼が遅くなりました。 申し訳ありません。 こう言う方法もあるんですね。参考にさせていただきます。

  • notnot
  • ベストアンサー率47% (4900/10358)
回答No.1

文字列など、= < > で比較できるならば、 myArray.sort(function(a,b) {return a==b?0:a>b?1:-1;});

whosfoo
質問者

お礼

お礼が遅くなり申し訳ありません。 この記述で動作はしました。 ありがとうございます。

関連するQ&A