Caractère de délimiteur le moins utilisé dans le texte normal <ASCII 128

Pour des raisons de codage qui vous horrifieraient (je suis trop gêné pour le dire), je dois stocker un certain nombre d’éléments de texte dans une seule chaîne.

Je les délimiterai en utilisant un personnage.

Quel personnage est le meilleur à utiliser pour cela, c.-à-d. Quel personnage est le moins susceptible d’apparaître dans le texte? Doit être imprimable et probablement moins de 128 en ASCII pour éviter les problèmes de parameters régionaux.

En supposant une raison embarrassante, vous ne pouvez pas utiliser le format CSV. Prenez des exemples de données et effectuez un simple compte de caractères pour chaque valeur 0-127. Choisissez l’un de ceux qui ne se produisent pas. S’il y a trop de choix, obtenez un plus grand dataset. Cela ne prendra pas beaucoup de temps pour écrire et vous obtiendrez la meilleure réponse pour vous.

La réponse sera différente pour différents domaines de problèmes, donc | (pipe) est commun dans les scripts shell, ^ est commun dans les formules mathématiques, et il en va probablement de même pour la plupart des autres caractères.

Je pense personnellement que j’irais pour | (pipe) si on lui donne le choix, mais aller avec des données réelles est le plus sûr.

Et quoi que vous fassiez, assurez-vous d’avoir élaboré un plan d’évacuation!

Probablement | ou ^ ou ~ vous pouvez également combiner deux caractères

Je choisirais “séparateur d’unité” code ascii “US”, ascii 30 (0x1F)

Dans l’ancien temps, la plupart des choses se faisaient en série, sans access aléatoire. Cela signifiait que quelques codes de contrôle étaient intégrés dans ASCII.

 ASCII 28 (0x1C) File Separator - Used to indicate separation between files on a data input stream. ASCII 29 (0x1D) Group Separator - Used to indicate separation between tables on a data input stream (called groups back then). ASCII 30 (0x1E) Record Separator - Used to indicate separation between records within a table (within a group). These roughly map to a tuple in modern nomenclature. ASCII 31 (0x1F) Unit Separator - Used to indicate separation between units within a record. The roughly map to fields in modern nomenclature. 

Unit Separator est en ASCII, et il existe un support Unicode pour l’afficher (généralement un “us” dans le même glyphe) mais de nombreuses fonts ne l’afficheront pas.

Si vous devez l’afficher, je vous recommande de l’afficher dans l’application, une fois analysée dans les champs.

Que diriez-vous d’utiliser un format de style CSV? Les caractères peuvent être échappés dans un format CSV standard, et il existe déjà de nombreux parsingurs déjà écrits.

Vous avez dit “imprimable”, mais cela peut inclure des caractères tels qu’un onglet (0x09) ou un stream de formulaire (0x0c). Je choisis presque toujours des tabs plutôt que des virgules pour les fichiers délimités, car les virgules peuvent parfois apparaître dans le texte.

(Fait intéressant, la table ascii a des caractères GS (0x1D), RS (0x1E) et US (0x1F) pour les séparateurs de groupe, d’enregistrement et d’unité, quels qu’ils soient / étaient.)

Si par “imprimable” vous voulez dire un personnage qu’un utilisateur pourrait reconnaître et taper facilement, j’irais pour le tuyau | symbole en premier, avec quelques autres caractères étranges ( @ ou ~ ou ^ ou \ , ou backtick que je n’arrive pas à entrer ici) comme une possibilité. Ces caractères +=!$%&*()-'":;<>,.?/ Semblent être plus susceptibles de se trouver dans les entrées utilisateur. Comme pour le soulignement _ et le hachage # et les crochets {}[] I ne sais pas

En utilisant des langues différentes, ce symbole: ¬

s’est avéré être le meilleur. Cependant, je teste toujours.

Pouvez-vous utiliser un symbole de tuyau? C’est généralement le prochain délimiteur le plus commun après des chaînes délimitées par des virgules ou des tabulations. Il est peu probable que la plupart du texte contienne un canal, et ord (‘|’) renvoie 124 pour moi, ce qui semble correspondre à vos besoins.

Pour échapper rapidement, j’utilise des trucs comme celui-ci: disons que vous voulez concaténer str1, str2 et str3 ce que je fais:

 delimitedStr=str1.Replace("@","@a").Replace("|","@p")+"|"+str2.Replace("@","@a").Replace("|","@p")+"|"+str3.Replace("@","@a").Replace("|","@p"); 

puis pour récupérer l’utilisation originale:

 splitStr=delimitedStr.Split("|".ToCharArray()); str1=splitStr[0].Replace("@p","|").Replace("@a","@"); str2=splitStr[1].Replace("@p","|").Replace("@a","@"); str3=splitStr[2].Replace("@p","|").Replace("@a","@"); 

note: l’ordre de remplacement est important

son incassable et facile à mettre en œuvre

Pipe pour la victoire! |

Nous utilisons le format ascii 0x7f qui est pseudo-imprimable et qui est rarement utilisé régulièrement.

Cela peut être bon ou mauvais (généralement mauvais) en fonction de la situation et de la langue, mais gardez à l’esprit que Base64 peut toujours encoder le tout. Vous n’avez alors plus à vous soucier d’échapper ou de dérober différents motifs de chaque côté, et vous pouvez simplement séparer et diviser les chaînes en fonction d’un caractère non utilisé dans votre jeu de caractères Base64.

J’ai dû recourir à cette solution pour mettre des documents XML dans des propriétés / nœuds XML. Les propriétés ne peuvent pas contenir de blocs CDATA, et les nœuds ont échappé, car CDATA ne peut évidemment pas contenir d’autres blocs CDATA sans casser la structure.

Le CSV est probablement une meilleure idée pour la plupart des situations.

Eh bien, cela dépend dans une certaine mesure de la nature de votre texte, mais une barre verticale 0x7C ne se retrouve pas très souvent dans le texte.

Je ne pense pas avoir déjà vu une esperluette suivie d’une virgule en texte naturel, mais vous pouvez d’abord vérifier le fichier pour voir s’il contient le délimiteur, et si c’est le cas, utilisez une alternative. Si vous voulez toujours être en mesure de savoir que le délimiteur que vous utilisez ne provoquera pas de conflit, effectuez une boucle en vérifiant le délimiteur souhaité dans le fichier et, s’il existe, doublez la chaîne jusqu’à ce que le fichier n’ait plus de correspondance. . Peu importe qu’il y ait des chaînes similaires car votre programme ne recherchera que des correspondances de délimiteurs exactes.

Vous allez probablement devoir choisir quelque chose et ignorer ses autres utilisations.

 + 

pourrait être un bon candidat.

Les tuyaux et les carets sont les choix les plus évidents. Je noterais que si les utilisateurs sont censés taper la réponse entière, caret est plus facile à trouver sur n’importe quel clavier que ne l’est le tube.

Je ne sais pas si vous devez utiliser ASCII, mais si vous pouvez l’encoder dans UTF-8, vous pouvez trouver un symbole très obscur comme: (U + 2561) – dans lequel j’utilise beaucoup mes programmes

Vous pouvez également examiner la sérialisation des objects et créer de nouveaux champs pour tous les éléments dont vous pourriez avoir besoin.