Малюйте разом із процесором


289

Я натрапив на статтю, де студенти використовували мережевий трафік, щоб намалювати свій університет на графіку IPv6 в країні . [зображення]

Ваша мета проста у визначенні, але складна у здійсненні. Намалюйте текст MAIL (оскільки це одне з небагатьох слів, яке можна прочитати на 1D графіку) на графіку CPU.

Це має виглядати приблизно так:

Результат

Детальніше про те, що кваліфікується:

  • Код не повинен бути кросплатформенним (тому вам не знадобляться невідомі API для роботи).
  • Ви можете зафіксувати його в будь-якій загальній утиліті використання процесора.
  • Графік виглядає дещо гірше на іншій машині: я вам зараз довіряю.
  • Використання базового процесора% повинно бути безперервним, тому якщо ви генеруєте випадкову хвилю і виділите щось, що схоже на слово MAIL, це очевидно обман.
  • Ви можете вибрати максимальне завантаження, яке потрібно використовувати, але воно повинно бути досить значним, щоб чітко його бачити.
  • Ви повинні дотримуватися лінійності прикладу. (Для M це виглядає так: базовий%, потім раптовий приріст до вказаного максимуму, поступово падає на нижчий%, піднімається назад до максимуму і знову різке падіння до базового%.)
  • Якщо це не читається, виборці все-таки помітять.

Застосовуються стандартні лазівки. Опублікуйте зображення теж!


9
Я більше не бачу причини для закритого голосування. Я особисто вважаю це цікавим викликом, хоч і трохи специфічним для системи.
seequ

6
Проблема, яку я бачу з кодом гольфу, полягає в тому, щоб оцінити, наскільки розбірливим є досить розбірливий. Якщо ви можете придумати спосіб визначити це об'єктивно, це значно покращить виклик, але це все-таки приємна ідея!
Мартін Ендер

3
це насправді так само, як ваша картина, але я вам гарантую, якщо ви не викладете це словами, люди будуть тлумачити "намалювати ПОШУК" дуже вільно.
Мартін Ендер

33
+1, це так абсурдно, що я майже посміхнувся на смерть ... "це безумство ..." "божевілля .. ЦЕ КОДЕГОЛЬФ !!!"
vaxquis

5
Це жахливе запитання. Я б хотів, щоб я був досить розумним, щоб брати участь. Це насправді не має значення, мене цікавлять творчі рішення інших людей: P
Chris Cirefice

Відповіді:


117

Пітона, 143

from time import*
while 1:
 sleep((ord('00012345654321000~~~D:6300036:D~~~000~~~000DDDD~~~~~'[int(time())%52])-48)*0.001);x=10**5
 while x:x-=1

Кожному символу рядка відповідає одна секунда активності, від символу ASCII 0(максимум навантаження) до ~(дуже невелике навантаження). Програма працює на циклі, синхронізованому за часом, тому ви можете запускати кілька примірників для кращих результатів.

Я використовував Python 2.7.6 на OS X з Intel Core i7, але він повинен працювати на інших комп’ютерах, трохи налаштувавши (відрегулюйте 0.001). Скріншот нижче зроблений із значною фоновою активністю.

ПОЧТА

Оновлення - мені вдалося створити чіткіший графік із time()/10меншою частотою оновлення:

ПОЧТА

І нарешті, ось більш гольф-версія ( 123 байти ) та її результат :

from time import*
while 1:
 sleep((ord('002464200~~A5005A~~00~~00DDD~~'[int(time()/2)%30])-48)*0.001);x=10**5
 while x:x-=1

250

Пітон, 358 281 268 221 194 байт

Монохромний такий у минулому році. Для використання двох процесів та системних дзвінків для досягнення двох кольорових графіків процесора!

import os,time
A='%-99o'%int('t12q2lxqkap48euoej9429cstbnazl63ubyryteo49u',36)
for i in'0123456':
 t=os.fork()
 while t<1:T=int(time.time())%50;(time.sleep,(id,os.urandom)[i<A[T+49]])[i<A[T]](1)

Вихід з монітора активності (OS X 10.9):

Графік монітора процесора Завантажте графік Графік діяльності монітора процесора

Повторюється на графіку історії CPU

Вихід з MenuMeters:

MenuMeters вихід

Всі виходи генерувались зі швидкістю оновлення 1с. Не виконується жодних значущих фонових завдань, хоча цей вихід досить легко вибиває будь-яке завдання з однопоточним процесором.

Цей код передбачає, що у вас є 8 ядер. Це має бути досить легко змінити для меншої кількості. Він портативний для систем Linux / UNIX (хоча він протестований лише на OS X) і повинен створювати однаковий двоколірний вихід для будь-якого монітора процесора, який може відрізняти користувача від системного процесорного часу.

По суті, це працює, виключаючи сім процесів, кожен з яких вирішить провести 1 секунду в режимі сну, спінінгу в користувальницькому режимі або обертання ядра. Спінінг в режимі ядра досягається за допомогою запиту великих даних у/dev/urandom , що примушує водія підтримувати /dev/urandomвитрачати багато "системних" процесорних циклів.

ЗРЕШЕНО [07/21]: Значно скорочено, використовуючи fork()замість multiprocessing.Process( /dev/urandomпрацює в будь-яких системах * NIX так чи інакше, тому це не зменшує мобільність). Однак зауважте, що програма тепер породжує фон завдання; вам, можливо, доведеться killall Python(або подібне) позбутися від процесорів, які їдять.


Я не втримався реалізувати ще кілька листів. Я отримав 16 літер плюс кілька символів:

~ /._ ПІН ANCHO ... ... VY

Повний алфавіт - "ACDFHILMNOPTUVWY", із символами "._ ~ / \". Напевно, може бути набагато більше символів, які можна представити.

Цілий код, що не використовується для додаткових літер:

from time import*
from multiprocessing import*

chars6 = {
'A': ('123456654321',
      '000123321000'),
'C': ('344556666666',
      '321110000000'),
'D': ('666666655443',
      '000000011123'),
'F': ('66666666666666',
      '00002222244444'),
'H': ('666664444466666',
      '000002222200000'),
'I': ('66666',
      '00000'),
'L': ('666662222222',
      '000000000000'),
'M': ('6665544334455666',
      '0004321001234000'),
'N': ('66665544336666',
      '00003322110000'),
'O': ('3445556666555443',
      '3221110000111223'),
'P': ('666666666555',
      '000003333444'),
'T': ('777776666677777',
      '444440000044444'),
'U': ('6666322236666',
      '4211000001124'),
'V': ('66654322345666',
      '33321000012333'),
'W': ('66542466424566',
      '43210133101234'),
'Y': ('66665433456666',
      '44333000033344'),
'_': ('1111111111',
      '0000000000'),
' ': ('000',
      '000'),
'.': ('12221',
      '10001'),
'~': ('44445544334444',
      '11223322112233'),
'/': ('2234566',
      '0012344'),
'\\': ('6654322',
       '4432100'),
}

s = 'ANCHOVY '
A = '000'.join(chars6[t][0] for t in s)
B = '000'.join(chars6[t][1] for t in s)

t=time()
f=open('/dev/urandom')
def F(n):
 while 1:T=int(time()-t)%len(A);[sleep,[].count,lambda x:f.read(4**9)][(n<int(A[T]))+(n<int(B[T]))](1)
for i in range(7):Process(target=F,args=(i,)).start()
F(7)

34
+1 для того, щоб надати літерам більше визначення, використовуючи 2 кольори
DustinDavis

4
І +1 для створення
листів,

1
Фактично A може бути належним чином виконаний (з отвором) з 4-х ниток. Потрібно встановити деякі кольори монітора процесора, щоб вони збігалися.
Руслан

@Ruslan: Про який монітор процесора ти думаєш? Мій монітор показує лише один сукупний графік з 0 <= система <= користувач <= 100 у кожній точці (що робить "отвори" неможливими AFAIK).
nneonneo

1
@nneonneo Я маю на увазі монітори, схожі на ваші. Дивіться цю картинку . Тут, якщо ми змінимо синій на зелений і червоний і фіолетовий на білий, ми отримаємо гарне "А" з отворами.
Руслан

133

C (Intel Core Duo + OS X / Darwin), 248 байт

#include <unistd.h>
#include <mach/mach_time.h>
#define M mach_absolute_time()
main(){char*s="JJJIHGFGHIJJJ@BDFHJJJHFDB@JJJJ@JJJJBBBBBBB";uint64_t i,t,y=1;for(;*s;s++){
for(i=40;i;i--){for(t=M+(*s&15)*9090909;t>M;)y*=7;usleep((11-(*s&15))*9091);}}}

Цей код приблизно такий же портативний, як і Велика піраміда Хеопса. Вибач за те. Значення, що повертаються mach_absolute_time(), залежать від обладнання, але на моїй машині значення збільшується приблизно один раз на наносекунд.

Ось результат:

Слово "MAIL" відображається в моєму графіку історії процесора

Існує два графіки, оскільки процесор має два ядра. Я встановлюю максимальне завантаження процесора приблизно на 90%, оскільки процес може перемикатися між ядрами щоразу, коли я дзвоню usleep(). При 100% навантаженні процес прив’язаний до одного ядра, а результати нерозбірливі ( див. Це, наприклад )


1
Хороша робота! Це виглядає дуже цікаво. Не могли б ви опублікувати невелике пояснення коду? :)
duci9y

1
я бачу брекети. чому в дужках для дужок є дужки? ви можете поставити сон у другий для останнього блоку циклу. я думаю, ти можеш трохи легше покататися на гольфі.
bebe

Чи не могли ви розмістити декларацію та ініціалізацію uint64_tзмінних у заголовку наступного forциклу?
Joey

74
+1: "Цей код приблизно такий же портативний, як і Велика Хеопсова піраміда"
Уве Кеїм

@ Так ні, змінні C повинні бути оголошені на початку блоку. помістивши його в блок ініціалізації for for, викличе помилку. звичайно, це стосується лише <C99
bebe

102

Рубі, 150 символів

a=(0..15).map{|i|[0.9-3*i*=0.02,i]}
[9,*a[0,11],*(z=a.reverse)[5,11],11,*z,*a,2,11,6,*[0.2]*9].map{|x,y|c=Time.now
1until Time.now-c>x/3
sleep y||x%3}

Це ще не все так коротко, але, на мій погляд, результат досить приємний, тому я зрозумів, що все-таки опублікую це. Як і у більшості інших рішень, вам, можливо, доведеться закріпити процес Ruby до певного ядра, префіксуючи його taskset -c $core.

Код - це просте поєднання спінінга / сну протягом певного часу, що повинно зробити його дещо портативним. Плавні градієнти створюються шляхом зміни співвідношення часу віджиму / сну.

MAIL письмовий монітор процесора

Зниження частоти вибірки процесора робить краї трохи кращими:

Нижня частота вибірки

Додавши в алфавіт AILMNUVWще кілька літер ( якісь впізнавані), ми також можемо написати кілька інших слів:

МАМА, МАЙ, СЕЛО

Ці фотографії генерувались із таким кодом:

def gradient num_samples, direction, base = 0.3, increment = 0.02, scale = 1
    range = [*0..num_samples]

    samples = case direction
        when :up then range.reverse
        when :down then range
        when :updown then range.reverse + range
        when :downup then range + range.reverse
    end

    samples.map{|i|
        i *= increment
        [base - scale * i, i]
    }
end

# letters are defined as a series of pairs of (spin-time, sleep-time)
# with the time in seconds
THIN_A = gradient(15, :updown, 0.2, 0.2/15)
A = gradient(15, :updown)
I = 2,0
L = 1.5,0, [[0.1,0.2]]*9
M = 2,0, gradient(9, :downup), 2,0
N = 1,0, gradient(9, :down), 2,0
U = 1,0, gradient(9, :downup, 0.1, 0.03, 0.1), 1,0
V = 0.5,0, gradient(12, :downup, 0.25, 0.02), 0.5,0
W = 0.5,0, [gradient(12, :downup, 0.25, 0.02)]*2, 0.5,0

[A,I,L,M,N,U,V,W].map{|i|
    # add 2 second pause after each letter
    i + [0,2]
}.flatten.each_slice(2){|x,y|
    # spin, then sleep
    c = Time.now
    1 until Time.now-c > x
    sleep y
}

Слова, які можна записати реалізованими літерами, можна знайти за допомогою

grep -E '^[aijlmnuvw]+$' /usr/share/dict/words 

4
+1 для розширення на більше слів!
Chris Cirefice

Ви могли скласти слово "алюміній".
Олівер Догерті-Лонг

@ OliverDaugherty-Long aluminium *
TuxCrafting

1
@ TùxCräftîñg Алюміній - це варіант написання, який має зайву букву, і це найдовше слово, яке я думаю, що працює.
Олівер Догерті-Лонг

48

Python, на Intel Pentium 4 3,0 ГГц, 180 166 145 141 138 байт

Подзвоніть з taskset -c 0 python cpu_graph_drawer.py.

taskset потрібен для обмеження процесу використання лише одного процесора / ядра (у моєму випадку гіперперебор).

from time import*;c=clock
a=[(3,.8),(3,5),(4,5),(1.3,5),(1.3,0)]
a.extend([(.1,.2)]*10)
for x,y in a:
    t=c()
    while c()-t<x:pass
    sleep(y)

Результат не такий великий. Цей із набором завдань -c 1


9
Я хотів би побачити це на моніторі процесора, який не згладжує криві ...
Szabolcs

1
Я теж, але мені не здається писати підкорений графік використання процесора, і gnome-system-monitorце єдине, що я знаю. Ви знайшли альтернативи, які мали б працювати на LMDE Cinnamon?
користувач80551

Увімкніть "Намалюйте процесор як складену діаграму площі", а всі кольори встановіть на чорний.
Техас Кале

@TejasKale Лінії все одно будуть вигнуті.
user80551

FYI: a=[...]+[(.1,.2)]*10замість цього можна пограти в куполі .extend.
nneonneo

46

Java 8, 482 символи

Кожен символ рядка означає кількість потоків, які будуть використані. Зображення зроблено на Intel Core i3 (2 ядра / 4 потоку).

результат

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class Mail{
public static void main(String[] args) throws InterruptedException{
Thread.sleep(15000);
for(char c:"123432234321000012343210000444000044441111111".toCharArray()){
ExecutorService executorService = Executors.newScheduledThreadPool(4);
for(int i=1;i<c-48;i++)executorService.execute(()->{while(!Thread.interrupted());});
Thread.sleep(1500);
executorService.shutdownNow();
}}}

Редагувати : більше гольф-версії (322 символів), однакова функціональність:

import java.util.concurrent.*;
class M{
public static void main(String[]a)throws Exception{
for(int c:"123432234321000012343210000444000044441111111".toCharArray()){
ExecutorService s=Executors.newFixedThreadPool(4);
while(c>48){c--;s.execute(()->{while(!Thread.interrupted());});}
Thread.sleep(1500);
s.shutdownNow();
}}}

1
Там є менше знаків, які інтерпретували як HTML і заплутували форматування.
Девід Конрад

Наступні два рядки повинні пояснити наступні два рядки @ValekHalfHeart. Виконавець - це потік (асинхронний диспетчер завдань), що виконує завдання (тут циклі) до переривання. Після його створення основний потік чекає 1,5 секунди, а потім перериває всі завдання.
PTwr

45
Щойно відкривши Eclipse, мій графік процесора написав "Простий протокол передачі пошти".
лолеск

21

C, 78 байт

Ви ніколи не говорили, що ми не можемо прийняти вклад користувача, так що ..

#include <unistd.h>
int main(){int x=0;for(;x<1<<26;++x);read(0,&x,1);main();}

Ця програма читає зі стандартного в, і кожен раз, коли вона читає персонаж, вона виконує безплатну процесору, витрачаючи цикл, а потім викликає основний знову. Ви контролюєте кількість використовуваного процесора часу, спамуючи клавішу введення з різною швидкістю.

Я провів це на Intel i3 4130T, який є досить новим процесором. Але ваш пробіг може відрізнятися, якщо він використовує більше або менше часу процесора, ніж це практично практично для вас, спробуйте зіграти зі зміною суми в циклі затримки.

Моя програма приголомшлива, тому що вона:

  • в основному є крос-платформою, вона повинна працювати з дуже невеликим вмістом на будь-якому * nix
  • перемагає питання
  • чудова гра з ендграми

Після кількох спроб я створив графік, який виглядав так:Графік процесора


Це допомагає обмежити його одним ядром процесора з набором завдань, a.la. taskset -c 1 [file]
Вуг

2
Я не бачу нічого в проблемних вимогах, що говорить про те, що наші матеріали будуть викликані якyes | [program]
Wug


1
"чудова гра з ендграйдом" змусила мене хахати. +1
Крістоф

1
Але ця відповідь занадто гарна, лазівки прокляті xD!
Чарівний восьминіг Урна
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.