Поясніть десятки


12

Давши десяткову форму у вигляді <float>, <precision>, ви малюєте графічне зображення десяткової частини (тобто дробу) поплавця. Приклади:

  1. Вхід:, 6.75, 4вихід:

    6||| 7
     ---- 
    

    6.75(перше число з входу) - це число, яке потрібно пояснити, 4(друге число з входу) - кількість тирев під трубами. 6дорівнює 6,75, 7є стелею 6.75. Кількість труб - це decimal part of first input number * second input number.

  2. Вхід:, 10.5, 6вихід:

    10|||   11
      ------
    
  3. Вхід:, 20.16, 12вихід

    20||          21
      ------------
    

    .16 насправді бере 1,92 труби, але оскільки я не можу намалювати 1,92 труби, я перекриваю її до 2.

  4. Вхід:, 1.1, 12вихід:

    1|           2
     ------------
    

    .1 в даному випадку становить 1,2 труби, тож це 1 патрубок.

  5. Також крайовий корпус. Вхід: 5, 4(тобто число є цілим числом), вихід:

    5    6
     ----
    

  • Кількість, яку слід пояснити, - це позитивний поплавок, обмежений лише вашими мовними здібностями.
  • Число точності - це ціле число, більше 2 (тобто мінімальна необхідна точність - 4). Це може бути і довільно великим.
  • > = n.5 труби округлені до n + 1 (тобто 1,5 округлено до 2, а 2,5 - до 3). <n.5 труби округлені до n (тобто 1,4 округлено до 1 і 2,4 - до 2).
  • Якщо це було б зручніше для вашої мови, ви можете взяти вхід як масив, наприклад [6.75, 4]. Якщо ви приймаєте вхід у зворотному порядку, тобто [4, 6.75]вкажіть його у своїй відповіді.

Чи можете ви бути більш конкретними щодо того, який саме потрібний формат виводу?
isaacg

@isaacg Я показав чотири приклади виходів. Що незрозуміло?
nicael

Здається, нерозкрито кілька кутових випадків. Наприклад , вхід 5.0 4: це зробити з 5в 6або з 4в 5, або є або прийнятним? Введення 1.25 2: чи має він 0 або 1 |с, і чому (тобто яке правило округлення)? Чи має бути перше число у введенні? Яка його максимальна точність та величина? Чи має бути друге число у вводі позитивним? Якщо це негативно, ми звернемо назад?
Пітер Тейлор

@Петер уточнено.
nicael

Я не думаю, що ви покрили правило округлення.
Пітер Тейлор

Відповіді:


6

CJam, 32 байти

l~1md@:X*mo'|*XSe]1$)NW$s,S*'-X*

Бере точність першої та десяткової секунди, розділених пробілом.

Запустити всі тестові справи.

Пояснення

l~   e# Read input and evaluate, pushing precision and decimal on the stack.
1md  e# Divmod 1, separating the decimal into integer and fractional part.
@:X  e# Pull up precision, store in X.
*mo  e# Multiply precision by fractional part and round.
'|*  e# Push that many vertical bars.
XSe] e# Pad with length X with spaces.
1$)  e# Copy integer part and increment.
N    e# Push linefeed.
W$   e# Copy integer part.
s,   e# Get number of digits as length of string representation.
S*   e# Push that many spaces, to indent the hyphens correctly.
'-X* e# Push X hyphens.

Так, здається, працює добре.
nicael

4

Математика, 119 байт

a=ToString;b=Array;a[c=Floor@#]<>{b["|"&,d=Round[#2#~Mod~1]],b[" "&,#2-d],a[c+1],"
"," "&~b~IntegerLength@c,"-"&~b~#2}&

Я спробував ... Тестування:

In[1]:= a=ToString;b=Array;f=a[c=Floor@#]<>{b["|"&,d=Round[#2#~Mod~1]],b[" "&,#2-d],a[c+1],"\n"," "&~b~IntegerLength@c,"-"&~b~#2}&;

In[2]:= f[6.75, 4]

Out[2]= 6||| 7
         ----

In[3]:= f[10.5, 6]

Out[3]= 10|||   11
          ------

In[4]:= f[20.16, 12]

Out[4]= 20||          21
          ------------

In[5]:= f[1.1, 12]

Out[5]= 1|           2
         ------------

In[6]:= f[5, 4]

Out[6]= 5    6
         ----

Чи можете ви надати робочу демонстрацію, або це неможливо?
nicael


3

Java, 253 206 181 байт

Збережено 47 байт завдяки @Kenney за допомогою вбудованих умов та змінних, що використовуються один раз, та сортування зайвих змінних.

Знову збережено 25 байт завдяки @Kenney, увімкнувши 2 петлі з потрійними операторами.

Чистий рядок маніпуляції:

Версія з вбудованими петлями (181 байт):

String m(float f,int p){int g=(int)f,i=0;String h="",q=""+g;int c=q.length();for(;i<c+p;)h+=i++<c?" ":"-";for(i=c;i<p+c;)q+=i++<c+Math.round((f-g)*p)?"|":" ";return q+(g+1)+"\n"+h;}

Версія з 4 петлями (206 байт):

String m(float f,int p){int g=(int)f,i=0;String h="",q=""+g;int c=q.length();for(;i++<c;)h+=" ";for(;i<=c+p;i++)h+="-";for(i=c;i<c+Math.round((f-g)*p);i++)q+="|";for(;i++<p+c;)q+=" ";return q+(g+1)+"\n"+h;}

Негольована версія:

String m(float f,int p){
//initialize some useful values, d is the number of pipes needed
int g=(int)f,d=Math.round((f-g)*p),i=0;
String h="",q=""+g;//append the floored value to the pipe string first
int c=q.length();
for(;i<c;i++)h+=" ";//pad hyphen string with spaces for alignment
for(++i;i<=c+p;i++)h+="-";//append hyphens
for(i=c;i<c+d;i++)q+="|";//append pipes
for(;i<p+c;i++)q+=" ";//append spaces for padding
return q+(g+1)+"\n"+h;}//concatenate the strings in order, separating the strings with a UNIX newline, and return it.

Робочий приклад тут на ideone.com . Повна програма приймає введення STDIN як <float>,<precision>.

ПРИМІТКА: Круги Java Math.round(float)використовуються RoundingMode.HALF_UPяк за замовчуванням, що є необхідною поведінкою ОП.

Вихід із поданих тестових випадків збігався з тим, що надав ОП.


Сподіваюся, ви не заперечуєте! Ви забули видалити a(не використовується), налаштовуючи Вас на 233. Ви можете заощадити ще 23 , щоб отримати в 210 байт: заміна q.length()з bекономить 13: int g=(int)f, b=(""+g).length(), c=b, i=0;. Приріст ітератора в стані з forекономить 6 і вбудовування d(використовується один раз) економить 4: int c = b; for(;i++<b;)h+=" "; for(;i++<=b+p;)h+="-"; for(i=c;i<c+Math.round((f-g)*p);i++)q+="|"; for(;i++<p+b;)q+=" ";.
Кенні

Також хтось запропонував використовувати фактичну нову лінію замість послідовності евакуації, але оскільки я перебуваю в Windows, це CRLF, 2 байти все одно дано\n
Tamoghna Chowdhury

Ніцца - так, bзастаріває як добре ;-) Ви все ще можете зберегти 1 байт в 2 для: for(;i++<=c+p;). Ви можете зберегти файл із закінченнями рядків Unix у Windows, але, на жаль, Java не дозволяє багаторядкові рядки ..
Кенні

@Kenney, ні. Я спробував це. Це призводить до несогласованих дефісів. Ява не є потрібною людиною для роботи.
Tamoghna Chowdhury

Я знизив його до 181 байта, використовуючи лише 2 для циклу:for(;i<c+p;)h+=i++<c?" ":"-";for(i=c;i<p+c;)q+=i++<c+Math.round((f-g)*p)?"|":" ";
Кенні

3

Javascript ES6, 105 104 байт

(f,p)=>(i=f|0)+("|".repeat(j=(f-i)*p+.5|0)+" ".repeat(p-j))+(i+1)+(`
`+i).replace(/\d/g," ")+"-".repeat(p)

Збережено 1 байт завдяки, гм, як ви все одно набираєте ՊՓԼՃՐՊՃՈԲՍԼ?


Вибачте, я не зрозумів, що тире є частиною результату, я подумав, що вони просто там, щоб візуалізувати пробіли.
Ніл

(f,p)=>(i=f|0)+("|"[r="repeat"](j=(f-i)*p+.5|0)+" "[r](p-j))+(i+1)+("\n"+i).replace(/\d/g," ")+"-"[r](p)
Mama Fun Roll

О так, замініть \nфактичним новим рядком. І обов’язково загортайте його в рядки шаблону.
Mama Fun Roll

2

Haskell, 113 байт

(%)=replicate.round
s=show
x!y|(n,m)<-properFraction x=[s n,(y*m)%'|',(y-y*m)%' ',s$n+1,"\n",s n>>" ",y%'-']>>=id

Приклад використання:

*Main> putStrLn $ 20.16 ! 12
20||          21
  ------------

properFractionрозбиває десятковий на цілу і дрібну частину. Вихід - це перелік частин (початкове число, бари, пробіли, ...), які об'єднані в один рядок (через >>=id).


Чи можна побачити демонстрацію цього інтернету?
nicael

@nicael: демо (із mainобгорткою для повної програми).
німі

Схоже, все гаразд (btw: перевірено там , подумайте, що це більш зручний компілятор).
nicael

2

MATL , 49 байт

2#1\tYUbiXK*Yo'|'1bX"tnKw-Z"hb1+YUhht4Y2m13*_45+c

Використовує випуск 6.0.0 мови / компілятора. Працює на Matlab або Octave.

Приймає числа в тому ж порядку, що і в виклику.

Приклади

>> matl
 > 2#1\tYUbiXK*Yo'|'1bX"tnKw-Z"hb1+YUhht4Y2m13*_45+c
 >
> 20.16
> 12
20||          21
  ------------

>> matl
 > 2#1\tYUbiXK*Yo'|'1bX"tnKw-Z"hb1+YUhht4Y2m13*_45+c
 >
> 5
> 4
5    6
 ----

Пояснення

2#1\       % implicit input 1st number. Separate decimal and integer part
tYU        % duplicate integer part and convert to string
biXK*Yo    % input 2nd number. Copy it. Multiply by decimal part of 1st number and round
'|'1bX"    % row vector of as many '|' as needed
tnKw-Z"    % row vector of as many spaces as needed
h          % concat horiontally
b1+YUhh    % integer part of 1st number plus 1. Convert to string. Concat twice
t4Y2m      % detect numbers in this string
13*_45+c   % transform numbers into spaces, and non-numbers into '|'
           % implicitly display both strings

У вас є онлайн-перекладач?
nicael

Ще немає :-( Роботи на Матлабі чи Октаві
Луїс Мендо

2

Perl, 90 байт

print$f,"|"x($d=.5+($b=pop)*(($a=pop)-($f=0|$a))),$"x(1+$b-$d),$f+1,$/,$"x length$f,"-"x$b

Очікує введення в якості аргументів командного рядка. Збережіть у файлі (скажімо 90.pl) і запустіть якperl 90.pl 6.75 4

З коментарями

print $f,                        # floored input (initialized below due to expr nesting)
      "|" x ($d=.5+              # rounded pipe count (`x` operator casts to int)
             +($b=pop)           # second argument  (executed first)
             *( ($a=pop)         # first argument   (executed second)
               -($f=0|$a) )      # minus floored first argument = fractional part
            ),
      $"x(1+$b-$d),              # spaces
      $f+1,                      # floored + 1
      $/,                        # newline
      $"  x length $f,           # 2nd line alignment
      "-" x $b                   # the 'ruler'

1

Козирка , 31 27 байт

CFv1%C*D'|^w1P-Y^vHXNY^w'-^

Подібно до більшості інших відповідей. Я побачу, чи зможу більше пограти в гольф. Вхід може бути розділений комою, розділений пробілом або майже будь-чим.

Не змагаючись, тому що Stackgoat був зроблений після цього виклику

Пояснення

CF   // Input, floored, push to stack
v1%  // Decimal part
C*   // Times second part
D    // Duplicate that result
'|^  // Repeat | by previous number
w    // Second input
1P   // Move # of |'s to the top of stack
-    // Subtract
Y^   // Repeat " " by above number
vH   // Ceil first input
X    // Newline
Z+   // Add to 
N    // Get length of first #
Y^   // Repeat by spaces
w'-  // Repeat - second input times

1

Луа, 157 байт

Довго, але не можна знайти коротше рішення

function f(d,n)r=""a=math.floor(d)d,s=d-a,a..r for i=1,#s do r=r.." "end for i=1,n do s,r=s..(i-.5>n*d and" "or"|"),r.."-"end s=s..a+1 return s.."\n"..r end

Безумовно

function g(d,n)
  r=""
  a=math.floor(d)
  d,s=d-a,a..r                         -- d now contains its decimal part
  for i=1,#s do r=r.." "end            -- padding the hyphens
  for i=1,n
  do
    s,r=s..(i-.5>n*d and" "or"|"),r.."-"
    -- s is concatenated with a "|" if i-.5>n*d, a space otherwise
  end
  s=s..a+1
  return s.."\n"..r
end

Ви можете протестувати lua онлайн , наступні тестові випадки можуть бути корисні :)

function f(d,n)r=""a=math.floor(d)d,s=d-a,a..r for i=1,#s do r=r.." "end for i=1,n do s,r=s..(i-.5>n*d and" "or"|"),r.."-"end s=s..a+1 return s.."\n"..r end
print(f(16.75,4))
print(f(5,4))
print(f(20.16,12))

1

C, 233 231 байт

#include <stdlib.h>
#include <math.h>
i,n,l;main(c,v)char**v;{double m;l=atol(v[2]);n=(int)(modf(atof(v[1]),&m)*l+0.5);c=printf("%.f",m);for(;i++<l;)putchar(i>n?32:'|');printf("%.f\n",m+1);printf("%*s",c,"");for(;--i;)putchar(45);}

Безголівки:

#include <stdlib.h>
#include <math.h>
i,n,l;

main(c,v)
char**v;
{
    double m;
    l=atol(v[2]); /* Get length from command line */
    n=(int)(modf(atof(v[1]),&m)*l+0.5); /* Get number of pipes and lower limit */
    c=printf("%.f",m); /* print lower limit */

    /* print pipes and spaces */
    for(;i++<l;)
            putchar(i>n?32:'|');

    /* print upper limit */
    printf("%.f\n",m+1);

    /* print spaces before dashes */
    printf("%*s",c,"");

    /* print dashes */
    for(;--i;)
            putchar(45);
}

1

Python 3, 116 108 байт

def f(F,P):l=int(F);h,p=str(l+1),int((F-l)*P+.5);l=str(l);print(l+"|"*p+" "*(P-p)+h);print(" "*len(l)+"-"*P)

посилання на trinket.io

Дякую Seeq за збереження кількох символів.

Перша версія:

def f(F,P):
 l=int(F)
 h,s,p=str(l+1)," ",int((F-l)*P+.5)
 l=str(l)
 print(l+"|"*p+s*(P-p)+h)
 print(s*len(l)+"-"*P)

Негольована версія:

def frac(F,P):
        low = int(F)
        high = low+1
        pipes = int((F-low)*P+.5)
        print(str(low)+"|"*pipes+" "*(P-pipes)+str(high))
        print(" "*len(str(low))+"-"*P)

Чи можете ви надати робочу демонстрацію?
nicael

Це посилання на trinket.io має працювати: trinket.io/python/409b1488f8
Джек Броунштейн

Насправді потрібно менше символів, щоб просто використовувати літерал простору, ніж зберігати його. Ви також можете просто з'єднати всі рядки за допомогою ;. Ви використовуєте лише hодин раз, тому вам слід також вбудувати його. Треба було зберегти кілька символів.
seequ

@Seeq Хороший улов на космос-буквал. На початку я друкував пробіли білого пробілу в кінці другого рядка; після того як я зрозумів, що це було непотрібно, я не перевіряв код на заощадження. Це hскладніше. Для конкатенації та lenфункціонування в останніх двох рядках має працювати lрядок, тому hїї потрібно буде замінити на str(int(l)+1). Налаштування hперед перетворенням lекономить кілька символів.
Джек Браунштейн
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.