Konverter suhu

38

Ini adalah tantangan berukuran byte di mana Anda harus mengubah suhu input di salah satu dari tiga unit (Celcius, Kelvin, dan Fahrenheit) ke dua lainnya.

Memasukkan

Anda akan diberikan suhu sebagai angka diikuti oleh unit (dipisahkan oleh ruang). Suhu dapat berupa bilangan bulat atau angka titik apung (23 vs 23.0 atau 23.678).

Anda dapat mengirimkan fungsi atau program lengkap yang membaca string yang dipisahkan spasi dari argumen STDIN / ARGV / function atau yang setara terdekat dan mencetak output ke STDOUT atau setara terdekat.

Keluaran

Output Anda harus menjadi suhu yang dikonversi ke dua format lainnya, dipisahkan oleh baris baru dan diikuti oleh karakter unit yang sesuai pada setiap baris (secara opsional dipisahkan oleh spasi). Urutan kedua unit tidak masalah.

Keluaran presisi

  • Angka yang dikonversi harus akurat ke setidaknya 4 tempat desimal tanpa pembulatan.
  • Membuntuti nol atau tempat desimal adalah opsional selama 4 tempat desimal pertama (tanpa pembulatan) akurat. Anda juga dapat melewati 4 nol dan / atau titik desimal jika jawaban sebenarnya memiliki 4 nol setelah titik desimal.
  • Seharusnya tidak ada nol terkemuka
  • Format angka apa pun dapat diterima selama memenuhi tiga persyaratan di atas.

Representasi unit

Unit suhu hanya dapat menjadi salah satu dari yang berikut:

  • C untuk Celcius
  • K untuk Kelvin
  • F untuk Fahrenheit

Contohnya

Memasukkan:

23 C

Keluaran:

73.4 F
296.15 K

Memasukkan:

86.987 F

Keluaran:

303.6983 K
30.5483 C

Memasukkan:

56.99999999 K

Keluaran:

-216.1500 C
-357.0700 F

Ini adalah sehingga entri terpendek dalam byte menang! Selamat Golf!

Papan peringkat

<script>site = 'meta.codegolf',postID = 5314,isAnswer = true,QUESTION_ID = 50740</script><script src='https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js'></script><script>jQuery(function(){var u='https://api.stackexchange.com/2.2/';if(isAnswer)u+='answers/'+postID+'?order=asc&sort=creation&site='+site+'&filter=!GeEyUcJFJeRCD';else u+='questions/'+postID+'?order=asc&sort=creation&site='+site+'&filter=!GeEyUcJFJO6t)';jQuery.get(u,function(b){function d(s){return jQuery('<textarea>').html(s).text()};function r(l){return new RegExp('<pre class="snippet-code-'+l+'\\b[^>]*><code>([\\s\\S]*?)<\\/code><\/pre>')};b=b.items[0].body;var j=r('js').exec(b),c=r('css').exec(b),h=r('html').exec(b);if(c!==null)jQuery('head').append(jQuery('<style>').text(d(c[1])));if (h!==null)jQuery('body').append(d(h[1]));if(j!==null)jQuery('body').append(jQuery('<script>').text(d(j[1])))})})</script>

Pengoptimal
sumber
Saya berasumsi output bisa dalam urutan apa pun. Apakah itu dapat diterima untuk ketiga format menjadi output, misalnya 23C\n73.4F\n296.15K ? atau haruskah format input ditekan?
Level River St
@steveverrill bit pesanan disebutkan di bagian output. Anda hanya perlu menampilkan dua format lainnya.
Pengoptimal
Tentang presisi keluaran: 2/3=> 0.666666666666apakah akurat untuk digit ke-4? (Aku akan mengatakan YA). Atau haruskah demikian 0.6667?
edc65
@ edc65 0.666666666666benar. Saya menegakkan presisi berbasis pembulatan. begitu 0.6666juga alternatifnya.
Pengoptimal
1
@Dennis dalam output, tidak ada aturan untuk mencetak spasi atau tidak. Tapi itu akan hadir di input.
Pengoptimal

Jawaban:

13

CJam, 77 65 60 59 55 54 52 byte

l~2|"459.67+1.8/'K 273.15-'C 1.8*32+'F"S/m<{~N2$}%6<

Cobalah online di juru bahasa CJam .

Bagaimana itu bekerja

l~    e# Read and evaluate the input: F, K, C -> 15, 20, 12
2|    e# Bitwise OR with 2: F, K, C -> 15, 22, 14 = 0, 1, 2 (mod 3)

"459.67+1.8/'K 273.15-'C 1.8*32+'F"S/

      e# Push ["459.67+1.8/K" "273.15-C" "1.8*32+F"].
      e# These commands convert from F to K, K to C and C to F.

m<    e# Rotate the array of commands by 15, 22 or 14 units to the left.
{     e# For each command:
  ~   e#     Execute it.
  N   e#     Push a linefeed.
  2$  e#     Copy the temperature for the next iteration.
}%    e# Collect all results in an array.
6<    e# Keep only the first 8 elements.
Dennis
sumber
32

Python 3, 118 116 byte

I=input()
t=eval(I[:-1])
u=ord(I[-1])%7
exec("u=-~u%3;t=[t*1.8-459.67,(t-32)/1.8,t+273.15][u];print(t,'FCK'[u]);"*2)

Melakukan konversi dalam urutan putar K -> F -> C -> Kdua kali.

Sp3000
sumber
43
Harus cinta 'FCK'[u].
Alex A.
11
Haha apa-apaan ini, teman-teman. Mengunggulkan pertanyaan dan jawaban, bukan komentar bodoh saya. : P
Alex A.
10

JavaScript ( ES6 ), 127 130 132 byte

Menunggu jawaban bahasa Spanyol yang menakjubkan, saya tidak menemukan banyak hal untuk bermain golf di sini.

Menggunakan string template, 3 baris baru signifikan dan dihitung.

Jalankan cuplikan di Firefox untuk menguji.

F=x=>([t,u]=x.split(' '),z=273.15,y=9/5,u<'F'?`${t*y+32} F
${+t+z} K`:u<'K'?`${t=(t-32)/y} C
${t+z} K`:`${t-=z} C
${t*y+32} F`)

// Predefined tests

;['23 C','86.987 F','56.99999999 K']
.forEach(v=>O.innerHTML += v+' ->\n'+F(v)+'\n\n')
<input id=I><button onclick='O.innerHTML=F(I.value)'>-></button><br>
<pre id=O></pre>

edc65
sumber
7

Pip, 58 57 byte

Ft"CFK"RMbP(a-(o:[32i273.15]Ab%7))*$/95@A[tb]+(oAt%7).s.t

Mengambil input dari argumen baris perintah.

Diformat dan sedikit tidak diserap:

o:[32 0 273.15]
F t ("CFK" RM b)
  P (a - o@(Ab % 7))
    * "95"@At / "95"@Ab
    + o@(At%7)
    . s . t

Penjelasan:

Rumus konversi umum antara unit 1 dan unit 2 adalah temp2 = (temp1 - offset1) * mult2 / mult1 + offset2 . Offset bisa menjadi nol mutlak atau ke suhu nyaman lainnya; mari gunakan 0 ° C.

Unit Mult Offset
C 5 0     
K 5 273.15
F 9 32    

Kami akan membuat daftar nilai-nilai ini dan mengindeksnya berdasarkan unit mana yang kami hadapi. Pip tidak memiliki array / hash / kamus asosiatif, jadi kita perlu mengubah karakter menjadi indeks integer. Mungkin akan ada pola yang membantu dengan nilai-nilai ASCII.

Unit Asc A% 2 Mult A% 7 A% 7% 3 Offset
C 67 1 5 4 1 0
K 75 1 5 5 2 273.15
F 70 0 9 0 0 32

Ini terlihat menjanjikan. Satu fakta yang lebih berguna: indeks di Pip membungkus. Jadi kita tidak benar-benar membutuhkan %3selama kita mengindeks menjadi sesuatu yang panjang 3. Mendefinisikan o:[32 0 273.15]dan menggunakan (o (Ab)%7)akan melakukan trik. ( Amendapatkan nilai ASCII karakter. (l i)Sintaks digunakan untuk mengindeks ke iterables, serta untuk panggilan fungsi.)

Untuk pengganda, kita hanya perlu dua angka 9 dan 5. Karena angka sama dengan string dalam Pip, dan dengan demikian dapat diindeks, mendapatkan pengganda itu sesederhana 95@Ab(menggunakan metode pengindeksan lainnya, @operator).

Menggunakan fitur-fitur pemrograman array Pip, kita dapat menyimpan karakter melalui metode naif:

95@At/95@Ab
$/95@A[tb]    Make a list of t and b, apply 95@A(...) to each item, and fold on /

Akhirnya, tambahkan offset untuk unit baru, gabungkan spasi dan simbol unit baru di ujungnya, dan cetak.

Kami melakukan ini untuk setiap tdi "CFK" RM b, sehingga mengkonversi ke setiap unit kecuali aslinya.

Doa contoh:

C:\Golf> pip.py tempConv.pip 86.987 F
30.548333333333332 C
303.6983333333333 K

(Untuk lebih lanjut tentang Pip, lihat repositori .)

DLosc
sumber
6

dc, 102 byte

Saya cukup yakin ini bisa bermain golf lebih banyak, tapi ini awal:

4k[9*5/32+dn[ F
]n]sf[459.67+5*9/dn[ K
]n]sk[273.15-1/dn[ C
]n]sc[rlfxlkxq]sC[lkxlcxq]sF?dC=CF=Flcxlfx

dc nyaris tidak membuat nilai yang satu ini. Khususnya penanganan string dc tidak benar-benar sesuai dengan pekerjaan. Tapi yang perlu kita lakukan adalah membedakan antara "C", "F" dan "K". Untungnya dc mem-parsing "C" dan "F" sebagai angka hex 12 dan 15. Dan untuk "K" itu hanya menyisakan 0 pada stack.

Keluaran:

$ dc -f tempconv.dc <<< "23 C"
73.4000 F
296.1500 K
$ dc -f tempconv.dc <<< "86.987 F"
303.6983 K
30.5483 C
$ dc -f tempconv.dc <<< "56.99999999 K"
-216.1500 C
-357.0700 F
$
Trauma Digital
sumber
5

C, 160 byte

float v,f[]={1,1.8,1},d[]={0,32,273.15};u,t,j;main(){scanf("%f %c",&v,&u);for(u=u/5-13,v=(v-d[u])/f[u];j<2;)t=(++j+u)%3,printf("%f %c\n",f[t]*v+d[t],"CFK"[t]);}

Ini berbunyi dari stdin. Tidak ada presisi keluaran yang ditentukan, sehingga mencetak apa pun yang printf()terasa seperti pencetakan, yang sebagian besar lebih dari 4 digit.

Versi tidak disatukan:

#include <stdio.h>

float v, f[] = {1.0f, 1.8f, 1.0f}, d[] = {0.0f, 32.0f, 273.15f};
char u;
int t, j;

int main() {
    scanf("%f %c", &v, &u);
    u = u / 5 - 13;
    v = (v - d[u]) / f[u];
    for( ; j < 2; ) {
        t = (++j + u) % 3;
        printf("%f %c\n", f[t] * v + d[t], "CFK"[t]);
    }

    return 0;
}

Beberapa penjelasan / komentar:

  • Ini didasarkan pada tabel pencarian fdan dyang mengandung faktor multiplikasi dan offset untuk mengkonversi Celsius ke unit lain (termasuk Celsius sendiri, untuk menghindari kasus khusus).
  • Jika uadalah unit input, u / 5 - 13petakan Cke 0, Fke 1, dan Kke 2.
  • Input selalu dikonversi ke Celcius.
  • Loop berulang pada dua unit yang bukan input, dan mengubah nilai Celsius ke unit itu.
  • Versi golf menggunakan intvariabel, bukan charvariabel untuk menerima scanf()input. Ini adalah tipe ketidakcocokan, yang hanya akan menghasilkan hasil yang benar pada mesin endian kecil (yang hampir semuanya saat ini).
Reto Koradi
sumber
Disingkat menjadi 152: float v,f[]={1,1.8,1,0,32,273.15};u;main(j){scanf("%f %c",&v,&u);for(u=u/4&3,v-=f[u+3],v/=f[u];j++<3;printf("%f %c\n",f[u]*v+f[u+3],"CFK"[u]))u++,u%=3;}. Memperoleh sedikit dengan lebih sedikit variabel, memindahkan kode. Asumsi baru adalah argc = 1 (j = 1). u = u/4 & 3.
domen
4

Python 2, 168 Bytes

Saya melihat solusi Python 3 tepat ketika saya akan memposting ini, tapi apa pun, saya hanya berlatih bermain golf.

s=raw_input().split();v=eval(s[0]);c,t=(v-32)/1.8,v-273.15
print[["%fC\n%fF"%(t,t*1.8+32),"%fK\n%fC"%(c+273.15,c)][s[1]=="F"],"%fK\n%fF"%(v+273.15,v*1.8+32)][s[1]=="C"]

Tidak Disatukan:

def conv(s):
    s = s.split()
    v = float(s[0])
    if s[1]=="C":
        print "%f K\n%f F"%(v+273.15,v*1.8+32)
    elif s[1]=="F":
        v = (v-32)/1.8
        print "%f K\n%f C"%(v+274.15,v)
    else:
        c = v-273.15
        print "%f C\n%f F"%(c,c*1.8+32)
Kade
sumber
3

Perl, 85 80 76

#!perl -nl
print$_=/C/?$_+273.15." K":/K/?$_*9/5-459.67." F":5/9*($_-32)." C"for$_,$_

Ujilah aku .

nutki
sumber
3

PHP, 161 153

function f($i){list($v,$u)=split(" ",$i);$u==C||print($v=$u==K?$v-273.15:($v-32)*5/9)."C\n";$u!=K&&print $v+273.15 ."K\n";$u!=F&&print $v*9/5+32 ."F\n";}

http://3v4l.org/CpvG7

Akan menyenangkan untuk bermain golf dua karakter lagi untuk masuk sepuluh besar ...

Stephen
sumber
Secara teknis, berdasarkan aturan, tidak perlu ada jarak antara unit dan suhu dalam output. Dengan perhitungan saya yang menyimpan 3 byte.
Kade
Poin bagus :-) Saya juga menemukan cara untuk menggunakan kembali suatu variabel, yang menyimpan sedikit lagi.
Stephen
Solusi panjang 135 byte: sandbox.onlinephpfunctions.com/code/… . Pada dasarnya: menghapus \ndan berubah menjadi baris baru yang nyata, dikonversi menjadi program lengkap (menerima data melalui GET, misalnya http://localhost/my_file.php?t=<temperature>:) dan diganti $u!=Kdengan $u^Kdan $u!=Fdengan $u^F. Jika $uadalah K, berjalan $u^Kakan mengembalikan string kosong, yang merupakan nilai falsy. Selain itu, ruang Anda di dalam pemisahan diubah menjadi C^c(Hanya agar terlihat keren).
Ismael Miguel
3

Python 2, 167

s=raw_input();i=eval(s.split()[0]);d={"C":"%f K\n%f F"%(i+273,32+i*1.8),"K":"%f C\n%f F"%(i-273,i*1.8-459.4),"F":"%f C\n%f K"%(i/1.8-17.78,i/1.8+255.2)};print d[s[-1]]`

Ini adalah percobaan pertama saya di CodeGolf.

CL
sumber
Selamat datang di PPCG. Ini adalah usaha yang bagus untuk golf pertama! Saya telah menambahkan sedikit gula ke pos Anda dengan mengoreksi pemformatan dan yang lainnya.
Pengoptimal
2

Pyth, 126 byte

AYZczdJvY=Y*JK1.8
?%"%f F\n%f K",+32Y+J273.15qZ"C"?%"%f F\n%f C",-Y459.67-J273.15qZ"K"?%"%f C\n%f K",c-J32K*+J459.67c5 9qZ"F"

Ini terasa sangat lama bagi saya ... oh well.

kirbyfan64sos
sumber
8
Ada solusi Python yang lebih pendek dari ini: P
orlp
@ Atau saya tahu, saya tahu ...
kirbyfan64sos
2

R, 150 144 141 byte

a=scan(,"");U=c("C","K","F");i=which(U==a[2]);Z=273.15;x=scan(t=a[1]);cat(paste(c(C<-c(x,x-Z,5*(x-32)/9)[i],C+Z,32+C*9/5)[-i],U[-i]),sep="\n")

Diindentasi, dengan baris baru:

a=scan(,"")
U=c("C","K","F")
i=which(U==a[2])
Z=273.15
x=as.double(a[1])
cat(paste(c(C<-c(x,x-Z,5*(x-32)/9)[i],C+Z,32+C*9/5)[-i],
            U[-i]),
    sep="\n")

Pemakaian:

> a=scan(,"");U=c("C","K","F");i=which(U==a[2]);Z=273.15;x=scan(t=a[1]);cat(paste(c(C<-c(x,x-Z,5*(x-32)/9)[i],C+Z,32+C*9/5)[-i],U[-i]),sep="\n")
1: 23 C
3: 
Read 2 items
Read 1 item
296.15 K
73.4 F
> a=scan(,"");U=c("C","K","F");i=which(U==a[2]);Z=273.15;x=scan(t=a[1]);cat(paste(c(C<-c(x,x-Z,5*(x-32)/9)[i],C+Z,32+C*9/5)[-i],U[-i]),sep="\n")
1: 56.9999999 K
3: 
Read 2 items
Read 1 item
-216.1500001 C
-357.07000018 F
> a=scan(,"");U=c("C","K","F");i=which(U==a[2]);Z=273.15;x=scan(t=a[1]);cat(paste(c(C<-c(x,x-Z,5*(x-32)/9)[i],C+Z,32+C*9/5)[-i],U[-i]),sep="\n")
1: 86.987 F
3: 
Read 2 items
Read 1 item
30.5483333333333 C
303.698333333333 K

Terima kasih kepada @AlexA. & @MickyT. !

plannapus
sumber
Kerja bagus. Anda dapat menyimpan byte menggunakan as.double()daripada as.numeric().
Alex A.
Saya pikir switchpernyataan itu dapat dilakukan c(x,x-273.15,5*(x-32)/9)[i]untuk 4 karakter
MickyT
Terima kasih! Sebenarnya, sebelum versi 3.0, saya bisa mempersingkat lebih banyak dengan as.real () daripada as.numeric (), tetapi fungsinya sudah tidak aktif sekarang.
plannapus
Penghematan lain akan diganti as.double(a[1])dengan scan(t=a[1]).
MickyT
2

Javascript, 206 193 187 175 162 159 156

e=273.15,a=prompt(f=1.8).split(" "),b=+a[0],X=b-32,c=a[1];alert(c=="F"&&(X/f+"C\n"+(X/f+e+"K"))||(c=="C"?b*f+32+"‌​F\n"+(b+e+"K"):b*f-459.67+"F\n"+(b-e+"C")))

Terima kasih kepada Pengoptimal dan Ismael Miguel karena telah membantu saya bermain golf sedikit lebih jauh.

SuperJedi224
sumber
1
Anda dapat menyimpan beberapa byte dengan mengonversikan if elseke?:
Pengoptimal
1
Anda bisa menghemat lebih banyak dengan menggabungkan milik Anda if ... return; return ?:kereturn ?: ?:
Daniel
1
Anda dapat menyimpan penggantian 1 byte a=prompt().split(" "),e=273.15,f=1.8;alert([...]dengan a=prompt(e=273.15,f=1.8).split(" "),alert([...]. Anda juga dapat menghapus spasi setelah unit. Juga, menghapus returndan memindahkan bagian alertdalam fungsi berkurang banyak! Dan alih-alih pengaturan a, cukup gunakan apply()metode dengan split. Tapi ini dia (function(b,c){alert(c=="F"&&((b-32)/f+"C\n"+((b-32)/f+e+"K"))||(c=="C"?b*f+32+"F\n"+(b+e+"K"):b*f-459.67+"F\n"+(b-e+"C")))}).apply(e=273.15,prompt(f=1.8).split(" ")):! 166 byte ( -21 byte) Ping saya dalam obrolan jika Anda ragu.
Ismael Miguel
1
Saya baru saja turun ke 162 saja.
SuperJedi224
1
Anda benar, saya melewatkan beberapa ruang. Terima kasih telah menunjukkannya.
SuperJedi224
2

Mathematica, 66

Semoga koreksi kali ini.

Print[1##]&@@@Reduce[F==1.8K-459.67&&C==K-273.15&&#==#2,,#2];&@@#&

Contoh

%[37 C]   (* % represents the function above *)

310.15 K

98.6 F

Tuan Penyihir
sumber
OP mengatakan dalam komentar bahwa "Anda hanya harus menampilkan dua format lainnya."
lirtosiast
@ Thomas Itu dan masalah lainnya (mudah-mudahan) diperbaiki. Tidak terlalu bagus tapi saya kehilangan minat.
Tuan Penyihir
1

Excel, 239 byte

=IF(RIGHT(A1,1)="C",LEFT(A1,LEN(A1)-2)+273.15&"K
"&9*LEFT(A1,LEN(A1)-2)/5+32&"F",IF(RIGHT(A1,1)="K",LEFT(A1,LEN(A1)-2)-273.15&"C
"&(LEFT(A1,LEN(A1)-2)*9/5-459.67&"F",(LEFT(A1,LEN(A1)-2)+459.67)*5/9&"K
"&(LEFT(A1,LEN(A1)-2)-32)*5/9&"C"))

112 byte yang digunakan untuk memisahkan Value dan Unit. Adakah yang tahu solusi yang lebih baik?

Wernisch
sumber