2016-02-03 1 views
1

Bien que je suis sûr que cela a été répondu quelque part, je ne peux pas trouver où, donc je suis vraiment désolé si c'est une répétition. Et c'est parti.Utilisez awk pour supprimer la notation scientifique dans une colonne

J'ai un fichier (vraiment, j'ai beaucoup de fichiers) qui a des points de données X, Y et Z séparés par des espaces en trois colonnes. J'essaie de les tracer en 3D avec GNUplot, qui, malheureusement, ne semble pas très satisfait de la notation scientifique. Maintenant, je peux sed mon chemin à la notation (A * 10 ** B) au lieu de la notation (AE + B), mais GNUplot ne le reconnaît toujours pas. Je sais que je peux convertir de la notation scientifique avec printf "% .5f" (je pense que cinq chiffres seraient très bien), mais je ne peux pas trouver comment formater mon entrée afin que je puisse l'appliquer à plusieurs colonnes ou, mieux encore, comment contrôler le format de chaque colonne. Je peux convertir une seule valeur:

echo ""|awk '{printf "%.5f", $2}' k11edit.dat 

mais je ne peux pas l'obtenir pour gérer plusieurs colonnes, ni même de maintenir un espace entre les valeurs (un onglet serait très bien, aussi, je ne suis pas partielle un seul espace).

Voici quelques lignes de mon dossier:

0.995 8.1584E-004 -0.17051415E+01 
0.995 8.8934E-004 -0.17053282E+01 
0.995 9.6284E-004 -0.17055150E+01 
0.995 1.0363E-003 -0.17057018E+01 
0.995 1.1098E-003 -0.17058886E+01 
0.995 1.1833E-003 -0.17060754E+01 
0.995 1.2568E-003 -0.17062623E+01 
0.995 1.3303E-003 -0.17064493E+01 
0.995 1.4038E-003 -0.17066362E+01 
0.995 1.4773E-003 -0.17068232E+01 
0.995 1.5508E-003 -0.17070103E+01 
0.995 1.6243E-003 -0.17071973E+01 
0.995 1.6978E-003 -0.17073846E+01 

Oui, je suis conscient que la première colonne ne change pas dans ces quelques lignes, mais il plus bas (le fichier est ~ 30 000 lignes longues, donc j'ai pensé que quelques lignes suffiraient ici).

Pourriez-vous m'aider?

+0

Modifiez votre question pour afficher la sortie attendue étant donné que l'entrée de l'échantillon n'est pas claire, ce que vous essayez de faire. –

+0

Mon gnuplot (version 4.6) n'a pas de problème avec cette notation: 'splot 'k11edit.dat' u 1: 2: 3 w lp' montre vos points de données. –

Répondre

4

Sans voir votre résultat attendu, il est une estimation mais est-ce que vous voulez:

$ awk '{for (i=1;i<=NF;i++) printf "%.5f%s", $i, (i<NF?OFS:ORS)}' file 
0.99500 0.00082 -1.70514 
0.99500 0.00089 -1.70533 
0.99500 0.00096 -1.70551 
0.99500 0.00104 -1.70570 
0.99500 0.00111 -1.70589 
0.99500 0.00118 -1.70608 
0.99500 0.00126 -1.70626 
0.99500 0.00133 -1.70645 
0.99500 0.00140 -1.70664 
0.99500 0.00148 -1.70682 
0.99500 0.00155 -1.70701 
0.99500 0.00162 -1.70720 
0.99500 0.00170 -1.70738 

Si vous souhaitez un format différent pour chaque champ:

$ awk 'BEGIN{split("%.3f %.7f %.4f",fmt)} 
     {for (i=1;i<=NF;i++) printf fmt[i]"%s", $i, (i<NF?OFS:ORS)}' file 
0.995 0.0008158 -1.7051 
0.995 0.0008893 -1.7053 
0.995 0.0009628 -1.7055 
0.995 0.0010363 -1.7057 
0.995 0.0011098 -1.7059 
0.995 0.0011833 -1.7061 
0.995 0.0012568 -1.7063 
0.995 0.0013303 -1.7064 
0.995 0.0014038 -1.7066 
0.995 0.0014773 -1.7068 
0.995 0.0015508 -1.7070 
0.995 0.0016243 -1.7072 
0.995 0.0016978 -1.7074 
+1

J'ai aimé votre utilisation de '?:' Pour épeler le délimiteur assez pour expliquer votre code. Puisque c'est votre réponse et non la mienne, je n'ai pas commenté autrement. La deuxième forme peut être écrite sans strophe 'BEGIN' ni boucle:' awk '{printf "% .3f% s% 7f% s% .4f% s", $ 1, OFS, $ 2, OFS, $ 3, ORS} '' –

+1

C'est exactement ce que je cherchais. Merci beaucoup. – Fire

+0

@AdamKatz oui, je l'ai fait plus général que nécessaire pour cette question spécifique alors quand d'autres le chercheront à l'avenir et qu'ils n'ont pas 3 champs fixes ils peuvent voir comment le faire. –

0

Il est un moyen hacky de faire il en utilisant OFMT et forcer la conversion en chaîne.

$ awk -v OFMT='%.5f' '{print $1+"",$2+"",$3+""}' file 

0.99500 0.00082 -1.70514 
0.99500 0.00089 -1.70533 
0.99500 0.00096 -1.70551 
0.99500 0.00104 -1.70570 
0.99500 0.00111 -1.70589 
0.99500 0.00118 -1.70608 
0.99500 0.00126 -1.70626 
0.99500 0.00133 -1.70645 
0.99500 0.00140 -1.70664 
0.99500 0.00148 -1.70682 
0.99500 0.00155 -1.70701 
0.99500 0.00162 -1.70720 
0.99500 0.00170 -1.70738 

Cependant, il ne convertit pas si le nombre est un nombre entier.

+0

Il convertira les valeurs en nombres si vous utilisez '$ 1/1' plutôt que' $ 1 + "" ' –

+0

Oui, mais vous devez convertir des nombres en chaînes pour utiliser l'OFMT. Peu importe, c'est un hack et printf devrait être le moyen préféré. – karakfa

+0

Les entiers ne fonctionneront pas dans les deux cas. Vous auriez à faire 'a = 0.000001; imprime $ 1 + a, $ 2 + a, $ 3 + a' pour contourner cela ('a' est' ⅒⁽ⁿ⁺¹⁾' où 'ⁿ' est la précision désirée), et cela ferait des erreurs comme 0.000004 arrondir à tort . –