2010-02-23 14 views
6

tengo que tomar una serie de caracteres asiáticos mixtos (por ahora, asumir solamente kanji chino o japonés kanji/hiragana/katakana) y "alfanumérico" (es decir, , Enlgish, francés), y el recuento de la siguiente manera:usando javascript, ¿Cómo puedo contar una mezcla de caracteres asiáticos y palabras inglesas

1) contar cada caracteres asiáticos como 1; 2) cuente cada PALABRA alfanumérica como 1;

algunos ejemplos:

株式会社 MyCompany = 4 caracteres + 1 palabra = 5 en total 株式会社 マ イ コ = 7 cars


mi única idea hasta ahora es utilizar:

var wordArray=val.split(/\w+/); 

y después comprobar cada elemento para ver si su contenido son alfanuméricos (así contar como 1) o no (a fin de tomar la longitud de la matriz). Pero no creo que sea realmente muy inteligente y el texto que se cuenta puede ser de hasta 10 000 palabras, por lo que no es muy rápido.

Ideas?

+0

No se puede distinguir un carácter asiático de otros caracteres multibyte. – shinkou

+2

Claro que puedes. Ellos tienen diferentes valores, después de todo. – Annabelle

+1

Gracias a todos. Nos decidimos por: var charArray = val.match (/ \ w + | [^., \ UFF10- \ uFF19, \ uFF9E, \ uFF9F]/g); alerta (charArray.length); No estábamos interesados ​​en el recuento de palabras asiáticas, necesitábamos el recuento de caracteres más el recuento de palabras alfanuméricas. Tendremos que agregar algunos códigos de exclusión, creo, pero este es un buen comienzo. – user224513

Respuesta

-2

pienso que deseas bucle para todos los personajes, e incrementar un contador cada vez que el carácter actual está en una palabra diferente (según su definición) que la anterior.

-1

Usted puede iterar sobre cada carácter en el texto, examinando cada uno en busca de roturas de palabras. El siguiente ejemplo hace esto, contando cada uno (CJK) ideograma chino/japonés/coreano como una sola palabra, y el tratamiento de todas las cadenas alfanuméricas como palabras individuales.

Algunas notas sobre mi aplicación:

  1. Probablemente no maneja correctamente los caracteres acentuados. Probablemente desencadenarán saltos de palabras. Puede modificar el wordBreakRegEx para solucionarlo.

  2. cjkRegEx no incluye algunos de los rangos de puntos de código más esotéricos, ya que requieren 5 dígitos hexadecimales como referencia y el motor de expresiones regulares de JavaScript no parece permitirle hacer eso. Pero probablemente no tenga que preocuparse por esto, ya que ni siquiera creo que la mayoría de las fuentes los incluyan.

  3. deliberadamente me dejó Hiragana y Katakana de cjkRegEx, ya que no estoy seguro de cómo desea manejar estos. Dependiendo del tipo de texto con el que se trate, podría tener más sentido tratar las cadenas de caracteres como palabras sueltas. En ese caso, necesitaría agregar lógica para reconocer estar en una "palabra kana" versus en una "palabra alfanumérica". Si no le importa, solo necesita agregar sus rangos de puntos de código al cjkRegEx. Por supuesto, podrías tratar de reconocer los saltos de palabras dentro de las cadenas de kana, pero eso rápidamente se convierte en Muy Duro.

Ejemplo aplicación:

function getWordCount(text) { 
    // This matches all CJK ideographs. 
    var cjkRegEx = /[\u3400-\u4db5\u4e00-\u9fa5\uf900-\ufa2d]/; 

    // This matches all characters that "break up" words. 
    var wordBreakRegEx = /\W/; 

    var wordCount = 0; 
    var inWord = false; 
    var length = text.length; 
    for (var i = 0; i < length; i++) { 
    var curChar = text.charAt(i); 
    if (cjkRegEx.test(curChar)) { 
     // Character is a CJK ideograph. 
     // Count it as a word. 
     wordCount += inWord ? 2 : 1; 
     inWord = false; 
    } else if (wordBreakRegEx.test(curChar)) { 
     // Character is a "word-breaking" character. 
     // If a word was started, increment the word count. 
     if (inWord) { 
     wordCount += 1; 
     inWord = false; 
    } else { 
     // All other characters are "word" characters. 
     // Indicate that a word has begun. 
     inWord = true; 
    } 
    } 

    // If the text ended while in a word, make sure to count it. 
    if (inWord) { 
    wordCount += 1; 
    } 

    return wordCount; 
} 

El Unihan Database es muy útil para el aprendizaje de CJK en Unicode. También por supuesto, el Unicode home page tiene mucha información.

+0

No muy útil excepto por ejemplo pseudocódigo. 1) A la implementación de ejemplo le falta un corchete de cierre al final del ciclo for, rompiéndolo por completo. 2) Si arreglas eso, no cuenta las palabras inglesas correctamente. 3) Tampoco cuenta correctamente las palabras japonesas porque el autor omitió Hiragana y Katakana. – fotoflo

3

Desafortunadamente, RegExp de JavaScript no admite clases de caracteres Unicode; \w solo se aplica a caracteres ASCII (modulo algunos errores del navegador).

Sin embargo, puede utilizar caracteres Unicode en grupos, por lo que puede hacerlo si puede aislar cada conjunto de caracteres que le interese como rango. ej .:

var r= new RegExp(
    '[A-Za-z0-9_\]+|'+        // ASCII letters (no accents) 
    '[\u3040-\u309F]+|'+       // Hiragana 
    '[\u30A0-\u30FF]+|'+       // Katakana 
    '[\u4E00-\u9FFF\uF900-\uFAFF\u3400-\u4DBF]', // Single CJK ideographs 
'g'); 

var nwords= str.match(r).length; 

(Este intenta dar un recuento más realista de 'palabras' para japonés, contando cada ejecución de un tipo de kana como una palabra. Eso todavía no está bien, por supuesto, pero es probablemente más cercano que tratar cada sílaba como una palabra.)

Obviamente, hay muchos más caracteres que deberían tenerse en cuenta si se quiere 'hacerlo correctamente'. ¡Espero que no tengas personajes fuera del plano multilingüe básico, por ejemplo!

Cuestiones relacionadas