Страницы

Поиск по вопросам

понедельник, 25 марта 2019 г.

CloseHandle для INVALID_HANDLE_VALUE

Если функция CreateFile вернула INVALID_HANDLE_VALUE, нужно ли закрывать его функцией CloseHandle?


Ответ

В документации прямо написано, что аргументом функции должен быть валидный дескриптор.
Pameters hObject [in] A valid handle to an open object.

Получение курсов евро

Подскажите, где можно получать курсы валют, сейчас получаю с сайта cbr.ru XML файл, но порой вылетает ошибка, PHP что не удалось открыть стрим.
как правильно подключаться к cbr?
или дайте ссылку на другой ресурс, где можно получать курсы!
function getCurs($moneyCode){ // создаем объект для работы с XML $xml = new DOMDocument(); // ссылка на сайт банка $url = 'http://www.cbr.ru/scripts/XML_daily.asp?date_req=' . date('d.m.Y'); // получаем xml с курсами всех валют if ($xml->load($url)){ // массив для хранения курсов валют $result = array(); // разбираем xml $root = $xml->documentElement; // берем все теги 'Valute' и их содержимое $items = $root->getElementsByTagName('Valute'); // переберем теги 'Valute' по одному foreach ($items as $item){ // получаем код валюты $code = $item->getElementsByTagName('CharCode')->item(0)->nodeValue; // получаем значение курса валюты, относительно рубля $value = $item->getElementsByTagName('Value')->item(0)->nodeValue; // записываем в массив, предварительно заменив запятую на точку $result[$code] = str_replace(',', '.', $value); } // возвращаем значение курса, для запрошенной валюты return $result[$moneyCode]; }else{ // если не получили xml возвращаем false return false; }
}


Ответ

ЦБ РФ не любит когда вы делаете больше чем сколько-то запросов в день. Ваш скрипт делает запрос к сервисам ЦБ РФ каждый раз когда кто-то открывает страницу. Если у вас хотя бы 1000 просмотров страниц в день, то это значит 1000 обращений к сервису ЦБ РФ. Этого количества вполне может быть достаточно чтобы забанить вас.
Если даже у вас нет никаких посетителей, на том же сервере что и ваш могут быть другие сайты, у которых такой же скрипт. Или даже хуже: автор встречал случаи когда для конвертации валют в прайс-листе для каждой строчки и для каждой валюты делался запрос за курсами валют. В прайс-листе было под тысячу позиций, а это значит для каждого скаченного прайс-листа к сайту ЦБ РФ делалось несколько тысяч запросов. Будь я вебмастером сайта ЦБ РФ, я бы тоже за такое внёс любые IP в чёрный список!
Так или иначе, попасть в чёрный список сайта ЦБ РФ очень просто. В этом случае вы будете получать такую ошибку:
failed to open stream: Redirection limit reached
Ошибка возникает потому что сайт ЦБ РФ передаёт вам куки и просит их сохранить и использовать при следующем запросе. То есть, вам придётся эмулировать браузер. И даже если вы будете эмулировать браузер, с вашим скриптом вы всё равно можете попасть в бан, из которого эмуляцией браузера не выбраться: все запросы к сайту ЦБ РФ будут сбрасываться. Как ни крути, вашим скриптом нельзя пользоваться.
Частично нивелировать проблему можно если кешировать данные после получения как минимум на несколько часов. Всё равно они обновляются лишь пару раз в день. Это сработает если это ваш выделенный сервер и никто больше кроме вас не использует похожие скрипты, засыпающие ЦБ РФ запросами.
function getCBRRates() { $xml_daily_file = __DIR__.'/daily.xml';
// кеш на четыре часа if (!is_file($xml_daily_file) || filemtime($xml_daily_file) < time() - 7200) { if ($xml_daily = file_get_contents('http://www.cbr.ru/scripts/XML_daily.asp')) { file_put_contents($xml_daily_file, $xml_daily); } }
$result = array(); foreach (simplexml_load_file($xml_daily_file) as $el) { $result[strval($el->CharCode)] = (float) strtr($el->Value, ',', '.'); }
return $result; }
echo getCBRRates()['USD'];
Ещё лучше будет показывать данные прямо на стороне клиента, минуя серверную часть. Данные в подходящем формате можно взять с известного зеркала с курсами ЦБ РФ. Этот сайт хорошо себя зарекомендовал давней и надёжной работой.
$.getJSON("https://www.cbr-xml-daily.ru/daily_json.js", function(data) { $('#EUR').text(data.Valute.EUR.Value.toFixed(2)); }); €1 = руб.
Аналогично можно показывать курсы других валют, показывать изменение курса относительно прошлого дня, и так далее.
$.getJSON("https://www.cbr-xml-daily.ru/daily_json.js", function(data) { console.log(data.Valute.EUR); console.log(data.Valute.USD); console.log(data); });
Если вы посмотрите, там есть все необходимые данные и даже отсылки к архиву курсов валют.

Почему не работает if x % 2: --x?

Если число нечётное, то уменьшить его на единицу - что неверно в следующем способе?
if x % 2: --x
Код полностью: https://ideone.com/SLZsrn
import random
def gen_smth(): x = random.randint(0, 100) if x % 2: --x return x
for _ in range(100): print(gen_smth())
В выводе содержатся нечётные числа, хотя должны были получиться только чётные:
64 11 37 35 1


Ответ

В Python нету --x, как и x--, вместо них стоит использовать x -= 1
Ну и как Qwertiy сказал в комментариях, запись if True: --x работает, потому что здесь - используется в качестве унарного минуса

Может показаться странным, что --x является statement в Python, но если обратиться к формальному определению statement, то получаем следующую цепочку:
simple_stmt → expression_stmt → starred_expression → expression → conditional_expression → or_test → and_test → not_test → comparison → or_expr → xor_expr → and_expr → shift_expr → a_expr → m_expr → u_expr, где
u_expr включает в себя унарные выражения.

Зачем использовать “|=”, “&=” и т.п. в C++ вместо “=”?

Програмлю Arduino и читаю в интернете про PORT. Говорят, что какая-то там стабильность будет, если писать вместо = - |=, или &=. Так я так и не понял, для чего так писать и чем это отличается от обычного "равно"? Вот пример рабочего кода:
int main() {
DDRB = B00100000;
while(1) { PORTB |= B00100000; delay(1000); PORTB &= B00000000; delay(1000); } }
Если заменить все эти |=, и &= на =, то всё будет работать точно также (как мне кажется) и даже не изменится размер прошивки (скетча). Так возвращаемся к вопросу: Зачем "|=", "&=" и т.д. в c++?


Ответ

Если вопрос касается именно c++ - то это операторы.
|= - побитовое или с присвоением. &= - побитовое и с присвоением.
Подробнее про операторы тут
По сути, это упрощенный синтаксис для подобной записи:
a = a | b; // для |= a = a & b; // для &=
Думаю, стало немного яснее, при чем тут равно. Далее попробуем разобраться, для чего же сами операторы | и &. Они называются побитовое или и побитовое и соответственно.
Оператор | берет побитовое представление операндов, и в результате выполнения этого оператора вы получите число, побитовое представление которого будет содержать единицы на тех позициях, на которых хоть в одном из двух побитовых представлений операндов стояла единица. Например:
4 | 5 = 5; // или (в побитовом представлении) 100 | 101 = 101;
Заметим, что крайняя слева и справа единицы есть хоть в одном из двоичных представлений чисел, и поэтому после выполнения побитового или у нас есть число 101 (в бинарном представлении) или 5 (в десятичной системе счисления).
Оператор & берет побитовое представления операндов, и в результате выполнения этого оператора вы получите число, побитовое представление которого будет содержать единицы на тех позициях, на которых в обоих побитовых представлениях операндов стояли единицы. Например:
4 & 5 = 4; // или (в побитовом представлении) 100 | 101 = 100;
Заметим, что осталась лишь одна единица, которая есть и в первом, и в правом операнде.
Ну и совсем вплотную подойдя к вашей задаче - | и & применяются обычно для работы с побитовыми флагами. Это сделано для экономии места. К примеру, у вас есть переменная размером 4 байта или 32 бита. В таком случае в этой переменной можно хранить аж 32 флага.
Чтобы добавить флаг, нужно применить |
int flags = 0; // Добавим флаг на третьей справа позиции, ведь бинарное представление 4 - 100 flags |= 0x4;
Чтобы проверить, есть ли флаг, нужно применить &
// Бинарное и - по сути маска. И если на этой позиции была 1, // то результат будет отличен от 0 и условие будет верным if (flags & 0x4) { // сделать что-то }
Как-то так. Почему же работает с равно? Все просто. С равно вы по сути стираете предыдущее состояние переменной с флагами, и передаете ей только 1 флаг вместе с равно. Надеюсь, понятно объяснил...
UPD кстати, в вашем случае PORTB |= B00100000; добавляет флаг, а потом PORTB &= B00000000; убирает его (что логично, ведь на той позиции, на которой мы поставили флаг, в B00000000 единицы нет, и применив и мы по сути убрали флажок).
UPD2 кстати, в чистом c++ нет литералов вида B00000000, это фишка компилятора arduino. В c++ начиная с версии 14 можно использовать запись вида 0b00000000, чтобы представить бинарный литерал.

JS При клике переключаться на следующий div

Например есть

1
2
3
4

Как правильно будет описана функция JS Чтобы получить следующий результат. При нажатии присваивается класс active к первому div , при повторном нажатии класс удаляется и присваивается к следующему диву. если нажать Назад , то действие идет в обратном порядке.


Ответ

На скорую руку
$(document).ready(function () { $('.next').on('click', function () { if ($('div.active').index() == -1) { $('.box div:first-child').addClass('active'); } else { $('div.active').next('div').addClass('active'); $('div.active').prev('div').removeClass('active'); } }); $('.prev').on('click', function () { if ($('div.active').index() == -1) { /* без действий */ } else { $('div.active').prev('div').addClass('active'); $('div.active').next('div').removeClass('active'); } }); }); .active{ background:#ccc; }

1
2
3
4

Почему цикл while будет бесконечным?

var x = false; var c = false; setTimeout(function() {x = true; alert('from timeset ' + x);}, 1000); while(!c) { c = x; }


Ответ

В JS нет многопоточности, и цикл не передаст управление следующему ивенту пока не выполнится. Более подробнее про eventloop можно посмотреть тут

Нахождение одного из чисел, если дан НОК двух чисел и второе число

Не могу понять, как эту задачу можно решить без "тупого" перебора чисел от НОК/данное число, до самого НОК. Число, которое нужно найти, должно быть минимальным подходящим к данным.
Можно выразить искомое число через НОД(неизвестный)*НОК/данное_число, но тогда не понятно, как обратно идти от НОД к числу. Также можно разложить НОК и дынное число на простые множители, по ним искать третье (опорная точка -- произведение чисел, которые есть в разложении НОК но нет в разложении данного нам числа), но тут как раз перебор с проверкой (правда, чуть поменьше). Второй вариант сложнее при очень больших числах.
Перебором нельзя т.к. числа будут огромные. Написать код не прошу, просто интересна сама суть решения, правильно ли я вообще думаю.


Ответ

Раскладываем на простые множители НОК. Получаем список множитель-кратность (например, при разложении 12 будет два множителя - 2 с кратностью 2 и 3 с кратностью 1). Назовём его список1. Раскладываем на простые множители имеющееся число (назовём его список2). Далее обрабатываем оба списка, создавая список3.
Если некий множитель отсутствует в список1, но имеется в список2, задача нерешаема. Если кратность множителя в список1 меньше его кратности в список2, задача нерешаема. Если некий множитель имеется в список1, но отсутствует в список2, он помещается в список3 с той же кратностью, что и в список1 Если кратность множителя в список1 больше его кратности в список2, он помещается в список3 с той же кратностью, что и в список1 Если некий множитель имеется в список1 и список2 с одинаковой кратностью, он помещается в список3 с кратностью 0 (ноль).
Перемножая множители из список3 с учётом кратности, получаем минимальное решение. Остальные решения получаем увеличением кратности одного или нескольких множителей в список3, но не превышая их кратности в список1
Всё.

как обновлять график matplotlib в tkinter раз в 5 минут данными из базы данных?

Что нужно: Каждые 5 секунд, считываются координаты из БД и отображаются на графике matplotlib в окне tkinter.
Что сделано: рисуются только первый набор данных и не рисуются второй набор
ВОПРОС: как исправить чтобы рисовался сначала первый набор данных , а через 5 секунд второй?
Вот обновленный минимальный рабочий код:
from threading import Thread from queue import Empty, Queue import time import tkinter as tk from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg#, NavigationToolbar2TkAgg from matplotlib.figure import Figure
class tkChartGUI(tk.Frame):
def __init__(self, parent): tk.Frame.__init__(self, parent) self.parent = parent self.initUI()
def get_latest_data(self, dataid): x_array=[] y_array=[] if (dataid == 1): x_array=[1,2,3,4,5,6,7,8,9,10,11,12,13,14]; y_array=[0.5,0.7,0.3,1.0,0.6,0.9,0.5,0.2,0.1,0.5,0.33,0.55,0.3,0.6] if (dataid == 2): x_array=[1,2,3,4,5,6,7,8,9,10,11,12,13,14]; y_array=[0.1,0.2,0.3,0.4,0.5,0.6,0.7,0.8,0.9,1.0,1.1,1.1,1.2,1.3] return (x_array, y_array)
def initUI(self): self.parent.title("Simple chart") self.parent.geometry("800x600+300+100")
result_queue = Queue() Thread(target=self.get_latest_data, args=[result_queue], daemon=True).start()
x_array, y_array = self.get_latest_data(1)
f = Figure(figsize=(5, 3), dpi=150) a = f.add_subplot(111) a.set_xlabel("Values_X") a.set_ylabel("Values_Y") a.yaxis.grid(True, which='major') a.xaxis.grid(True, which='major') a.plot(x_array, y_array)
canvas = FigureCanvasTkAgg(f, master=self.parent) canvas.show() canvas.get_tk_widget().grid(row=0,column=0)
def display_result(a, q): x_array = [] y_array = [] try: x_array = q.get(block=False) # get data y_array = q.get(block=False) a.plot(x_array, y_array) canvas.draw() except Empty: #a.clear() timeout_millis = round(100 - (5000 * time.time()) % 100) self.parent.after(timeout_millis, display_result, a, q)
def get_result(q): x_array, y_array = self.get_latest_data(2) q.put(x_array) # put data in FIFO queue x coords array q.put(y_array) # put data in FIFO queue y coords array
display_result(a, result_queue)
def onExit(self): self.quit()
def main(): root = tk.Tk() my_gui = tkChartGUI(root) root.mainloop()
if __name__ == '__main__': main()


Ответ

Чтобы постоянно не считывать данные из базы данных (polling), можно определить trigger, чтобы вызвать функцию (callback), когда в БД интересное событие произойдёт. К примеру, когда в нужную таблицу новое значение добавляется (Launch a Python Script from a sqlite3 Trigger):
CREATE TRIGGER tt AFTER INSERT ON t BEGIN SELECT got_y(NEW.y); END
Обновления графика происходят в got_y() обратном вызове, определённом в make_callback() ниже. Код похож на ответ c loop(), определённой с помощью .after(), с той разницей, что здесь функция вызывается, когда нужные данные готовы, вместо того чтобы периодически непрерывно новые данные запрашивать без блокировки:
#!/usr/bin/env python3 import datetime as DT import sqlite3 import random import threading import time import tkinter as tk from collections import deque
import matplotlib.pyplot as plt from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg from matplotlib.dates import date2num
def generate_data(db): # generate dummy data for the example while True: time.sleep(.1) db.execute('insert into t values(?)', (random.randrange(100),))
def make_callback(root): # plot something # see @MaxU answer https://ru.stackoverflow.com/q/801923/23044 n = 300
def get_t(): return date2num(DT.datetime.now()) xx = deque([get_t()], maxlen=n) yy = deque([0], maxlen=n) fig, ax = plt.subplots() ax.set_ylim(0, 100) line, = ax.plot_date(xx, yy, marker='') format_time = '{:%Y-%m-%d %H:%M:%S}'.format time_text = ax.text(0.5, 0.9, '', transform=ax.transAxes)
# add to GUI canvas = FigureCanvasTkAgg(fig, master=root) # A tk.DrawingArea. canvas.get_tk_widget().pack(fill=tk.BOTH, expand=True)
def got_y(y): # update plot xx.append(get_t()) yy.append(int(y)) line.set_data(xx, yy) ax.fill_between(xx, 0, yy, color='lightgrey') time_text.set_text(format_time(DT.datetime.now())) ax.relim() # update axes limits ax.autoscale_view(scaley=False) canvas.draw() return got_y
def main(): root = tk.Tk() # a dummy db for the example db = sqlite3.connect(':memory:', check_same_thread=False) db.execute('create table t(y)') db.create_function('got_y', 1, make_callback(root)) db.execute('CREATE TRIGGER tt AFTER INSERT ON t BEGIN SELECT got_y(NEW.y); END') threading.Thread(target=generate_data, args=[db], daemon=True).start() root.mainloop()
if __name__ == '__main__': main()
Здесь db.create_function() определяет какая Питон-функция используется в качестве got_y(y) обратного вызова. В примере, callback вызывается в дочернем потоке, что не всегда желаемо. Поток с generate_data() используется только для примера, фактически данные могут вставляться в базу данных из другого процесса или других машин. How to receive automatic notifications about changes in tables?

Для сравнения вот вариант с polling, где база данных постоянно опрашивается в фоновом потоке, используя простой цикл (про достоинства и недостатки цикла подробно описано в Как правильно сделать временный цикл?)
def poll_db(interval=5): while True: time.sleep(interval - time.time() % interval) # avoid drift emit(get_y_from_db())
здесь get_y_from_db() делает запрос к базе данных, а emit() генерирует событие для GUI:
#!/usr/bin/env python3 import random import threading import time import tkinter as tk
def get_y_from_db(): # generate dummy data time.sleep(random.random()) # emulate blocking function return random.randrange(100)
def poll_db(emit, interval=5): while True: time.sleep(interval - time.time() % interval) # avoid drift emit(get_y_from_db())
root = tk.Tk() root.bind('<>', lambda e, f=make_callback(root): f(e.y)) # subscribe threading.Thread(target=poll_db, args=[lambda y: root.event_generate('<>', when='tail', y=y)], daemon=True).start() root.mainloop()
Пример кода (где этот метод также используется): вывод процесса показывается в Tkinter GUI с помощью root.event_generate()

Не на всех реализациях можно root.event_generate() в фоновом потоке вызвать. В таких случаях можно использовать queue, чтобы данные между потоками передавать:
#!/usr/bin/env python3 import datetime as DT import random import threading import time import tkinter as tk from collections import deque from queue import Empty, Queue from time import time as timer
import matplotlib.pyplot as plt from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg from matplotlib.dates import date2num
def get_y_from_db(): # generate dummy data time.sleep(random.random()) # emulate blocking function return random.randrange(100)
def poll_db(emit, interval=1): # NOTE: interval is independant from the delay while True: time.sleep(interval) emit(get_y_from_db())
def start_polling_loop(root, q, delay): # plot something # see @MaxU answer https://ru.stackoverflow.com/q/801923/23044 n = 600
def get_t(): return date2num(DT.datetime.now()) xx = deque([get_t()], maxlen=n) yy = deque([0], maxlen=n) fig, ax = plt.subplots() ax.set_ylim(0, 100) line, = ax.plot_date(xx, yy, marker='') format_time = '{:%Y-%m-%d %H:%M:%S}'.format time_text = ax.text(0.5, 0.9, '', transform=ax.transAxes)
# add to GUI canvas = FigureCanvasTkAgg(fig, master=root) # A tk.DrawingArea. canvas.get_tk_widget().pack(fill=tk.BOTH, expand=True)
# update in a loop def loop(): timeout_millis = round(delay - (1000 * timer()) % delay) root.after(timeout_millis, loop) # avoid drift
try: y = q.get(block=False) except Empty: return # no new data
# update plot xx.append(get_t()) yy.append(y) line.set_data(xx, yy) ax.fill_between(xx, 0, yy, color='lightgrey') time_text.set_text(format_time(DT.datetime.now())) ax.relim() # update axes limits ax.autoscale_view(scaley=False) canvas.draw() root.after_idle(loop) # start
root = tk.Tk() q = Queue() threading.Thread(target=poll_db, args=[q.put], daemon=True).start() start_polling_loop(root, q, delay=40) root.mainloop()
Упрощённый вариант (с одним обновлением данных из потока), см. в Как сделать постоянное обновление окна Tkinter? Как избежать подвисания на время ожидания ответа от сервера. Ещё пример кода (где этот метод используется): вывод процесса показывается в Tkinter GUI, используя widget.after(), q.get()/q.put()

Нахождение угла между 2 точками (для движения машины к цели)

Проблема такая:
Нужно найти угол между точками X, Y.
К примеру, есть точки:
Координаты машины:
x: 1141.513916 y: -1162.998169
Координаты точки, куда нужно ей приехать:
x: 1162.112061 y: -1199.149658
Нужно как-то рассчитать угол между машиной и точкой.
Должно быть что-то такое:
if (angel < 5){ Turn_Car_Left(); }
if (angel == 5){ Ride_Forward(); }
if (angel > 5){ Turn_Car_Right(); }


Ответ

Вступление
Итак, начать стоит с того, что Вы поставили некорректное условие, так как угол -
геометрическая фигура, образованная двумя лучами (сторонами угла), выходящими из одной точки (которая называется вершиной угла).
В свою очередь луч -
часть прямой, состоящая из данной точки и всех точек, лежащих по одну сторону от неё. Любая точка на прямой разделяет прямую на два луча.
В свою же очередь одна единственная прямая проходит через 2 точки => для построения угла требуется части 2-х пересекающихся прямых (с одной общей точкой) => 2 * 2 - 1 = 3 точки
Таким образом мы получаем очевидный для всех факт: не может быть между двумя точками какого-либо угла

Немного теории
Отойдем ненадолго от разъяснений геометрии за N класс средней школы и все таки попытаемся догадаться, что же Вам нужно
Как я понимаю, Вы моделируете движение машины в плоскости xOy. Так как машина движется, она имеет некоторый вектор, характеризующий ее перемещение.
Предположу, что машина выехала из точки (0; 0) => если ее текущие координаты равны (x; y), то вектор перемещения равен { x - 0; y - 0; } = { x; y; }
Однако так как Вам требуется найти угол для поворота машины, Вам бы следовало использовать вектор ее скорости, но Вы нас обделили информацией о нем, так что предположу, что он сонаправлен с вектором перемещения
Итак. На данном шаге у нас есть вектор и точка, итого: 3 точки. Для расчета угла более чем достаточно
Далее находим направляющий вектор из начала координат в необходимую точку и находим наименьший угол между двумя имеющимися векторами (a и b) по формуле:
cos(α) = (a * b) / (|a| * |b|)

Пример
Попробуем на примере:
Пусть машина располагается в точке (1; 2.5), а пункт назначения - в точке (3; 3)

a = { 1; 2.5 } b = { 3; 3 }
cos(α) = (1*3 + 2.5*3) / (sqrt(1*1 + 2.5*2.5) * sqrt(3*3 + 3*3)) ≈ 0.91914503001
=>
α = arccos(0.91914503001) ≈ 0.404891786 rad ≈ 23.1985905 deg
Вот мы и получили заветный угол, который примерно равен 23 градусам
На сием курс геометрии окончен, переходим к программной реализации

Реализация
Набросаем такую функцию:
private static double GetAngle(Point Machine, Point Destination) { // Получим косинус угла по формуле double cos = Math.Round((Machine.X * Destination.X + Machine.Y * Destination.Y) / (Math.Sqrt(Machine.X * Machine.X + Machine.Y * Machine.Y) * Math.Sqrt(Destination.X * Destination.X + Destination.Y * Destination.Y)), 9); // Вернем arccos полученного значения (в радианах!) return Math.Acos(cos); }
Судя по значениям в Вашем примере, которые явно больше единицы, Вы используете не радианную, а градусную меру, а посему значение, которое вернет Вам функция, необходимо будет преобразовать по формуле:
dAngle = rAngle * 180 / Pi
То есть так:
// Переведем угол в градусы private static double ToDegrees(double Angle) => Angle * 180 / Math.PI;

Протестируем:
Пусть машина располагается в точке (-3; -3), а пункт назначения - в точке (3; 3)

Найдем угол:
Console.WriteLine(ToDegrees(GetAngle(new Point(-3, -3), new Point(3, 3)))); // 180
180 градусов, что, очевидно, является чистейшей правдой!

Итоги
Старайтесь не забывать, что программирование состоит не только из набора текста, но и из применения знаний некой предметной области, с которой Вы соприкасаетесь в рамках проекта.
Чего-то не знаете? Читайте и узнавайте по теме как можно больше!
И да, подчеркну, что представленный выше метод будет работать только если Ваша машинка прямолинейно удаляется от начала координат (т.е. векторы перемещения и скорости сонаправлены), однако стоит машине развернуться и поехать в сторону точки (0; 0), как все сломается! Чтобы решить проблему, Вам необходимо знать, в какую сторону движется автомобиль. Я не знаю деталей Вашей реализации, так что могу предложить кэшировать предыдущую точку, в которой был автомобиль, после чего уже передвигать его на новую. Тем самым Вы спокойно в любой момент времени найдете вектор скорости машины и примените его в расписанном выше алгоритме

Создание читабельной строки из крупного числа (6485251 => “6.485.251”)

Есть потребность выводить на экран крупные числа, но сделать это нужно так, чтобы юзер мог легко воспринимать это число, то есть добавить разделитель между каждыми 3-мя цифрами в числе Например: (6485251 --> "6.485.251")
Как можно реализовать метод, который будет принимать, допустим переменную типа "int" и возвращать "string" с разделителями?


Ответ

String.Format("{0:n}", 6485251 ); //вывод: 6,485,251.00 string.Format("{0:n0}", 6485251); //вывод: 6.485.251

В каких областях больше применяется C#, а в каких Java ? Помогите определиться с выбором [закрыт]

В каких областях больше применяется C#, а в каких Java ? Оба энтерпрайз, оба мобильные приложения: Android, WP7 (Mango). Стою перед выбором что в свободное время изучать. В будущем клепать формочки (и прописывать к ним события - утрируя конечно же) нет желания... Хочется чего-то интересного? что выбрать?


Ответ

на мой взгляд статья на википедии многое грамотно описывает: Сравнение C Sharp и Java лично я работаю с C# особенно мне нравится фреймворк ASP.NET MVC, на нём и фокусируюсь, хотя работал и с WinForms, WPF/Silverlight(не профессионально)

Как при помощи CSS сделать картинку черно-белой?

Здравствуйте. Как при помощи CSS сделать картинку черно-белой? UPD1 Инструменты серверного программирования недоступны. Только клиентский CSS.


Ответ

Мб объяснить заказчику, что браузер - не фотошоп?) А вообще вот, html5+css3+js

Как обнулить массив

Как можно быстро удалить все элементы из массива, который уже был объявлен ранее? $arr=null; удаляет сам массив, а не его содержимое.


Ответ

Быть может я чего-то не понял, но: var array = [1,2,3,4,5]; array = []; // :D

Проблемы с созданием метода для класса

Здравствуйте! Начал осваивать ООП и столкнулся с проблемой, решил написать класс matematik и несколько методов в нем. Первым стал возведение в степень. Вот код: public class matematik { public int result; public int erection (int a, int n) { if (n>0) { for(int i = 1; i <= n; i++) { result = 1; result = result * a; } return result; } if (n<0){ for(int i = n; i <= 1; i++){ result = 1; result = result/a; } return result; } } } Эклипс ругается на вот эту строчку "public int erection (int a, int n)" This method must return a result of type int. Подскажите новичку, что я делаю не так?


Ответ

// matematik - неправильно, правильно mathematic. // а кроме того в java принято называть классы с заглавной class Mathematic { // есть смысл сделать метод статичным, // - т.к. его выполнение не повлияет на состояние класса public static int power(int base, int power) {
// эта переменная не может быть полем // потому что нет смысла хранить временные данные за пределами данного // метода int result = 0; if (power > 0) { for (int i = 1; i <= power; i++) { result = 1; result = result * base; } // мы в любом случае будем возвращать результат // посему именно здесь можно не возвращать результат // return result; } else if (power < 0) { // чутье подсказывает что этот код работает неправильно for (int i = power; i <= 1; i++) { result = 1; result = result / base; } // мы в любом случае будем возвращать результат // посему именно здесь можно не возвращать результат // return result; }
// результат возвращаем в любом случае return result; } } имеет смысл рассмотреть частные случаи: 1) степень равна 0 2) степень равна 1 3) степень меньше 0 4) степень - дробное число последний частный случай подразумевает что у вас степень может быть не только целочисленным значением, но еще и дробным. а посему лучше поменять тип данных int на double, но не думаю что есть смысл рассматривать этот вариант, т.к. его реализация не так уж проста. с другой стороны возможность задания негативной степени показывает что на входе функции может быть дробное число (5^-2 = 1/5^2 = 1/25). код учитывая все вышесказанное: public static double power(double base, int power) { // сначала обрабатываем частные случаи // это нужно чтоб наш код не делал лишних действий
// возведение 0 в любую степень даст 0 // в случае когда степень будет отрицательной // придется делить на 0 if (0 == base) { return 0; }
// если степень равна единице, то выполнять возведение бесполезно // if (1.0 == power) { - неправильно (1.0 имеет тип double) // спасибо @avp что заметил, так будет правильно if (1 == power) { return base; }
// если степень отрицательная: то 2^(-3) = 1/(2^3) if (0 > power) { return power(1 / base, -power); }
// будет хранить результат в этой переменой double result = base;
// само вычисление for (int i = 1; i < power; i++) { result = result * base; }
return result; }

Как изменить названия кнопок в MessageBox в C#?

Как можно изменить названия кнопок в MessageBox в C#?


Ответ

Никак. Но можно создать форму нужных размеров, повесить там кнопки, информацию (label), и открывать её как MessageBox по виду, единственное лишний код будет, MessageBox для того и придуман что бы одной строчкой её показать и что-то так написать.
Открыть форму можно так:
Form form = new Form1(); form.ShowDialog();
На это форме помещаешь кнопку и обработчик.
Закрыть форму:
form.Close();

Стандарты комментирования исходного кода

Когда сталкиваюсь с opensource-проектами, в исходниках часто вижу комментарии такого типа: /** * Set the default fetch mode for this statement * @param mixed $mode fetch mode * @return CDbCommand * @see http://www.php.net/manual/en/function.PDOStatement-setFetchMode.php * @since 1.1.7 */ public function setFetchMode($mode) { $params=func_get_args(); $this->_fetchMode = $params; return $this; } Полный код библиотеки здесь Многие распространенные IDE этот формат комментирования понимают, и строят на его основе автодополнение кода. Это очень удобно. Да и читабельность кода на высшем уровне. Вот интересно, что за стандарт такой? Где с ним можно поподробнее познакомиться? И, если существуют другие стандарты для различных языков, про них тоже было бы интересно узнать.


Ответ

Причем тут вообще Doxygen? Это называется Docstring. В данном примере же приведен PHPDoc. Почитать документацию можно тут. IDE понимают только ограниченный набор тегов. Это, как-правило, теги: @deprecated - помечает класс/метод, как устаревший. В IDE такие методы отображаются перечеркнутые. @method - какой-либо метод. Соответственно в IDE будет работать автодополнение по этому методу, даже если его не существует. Так же если в качестве возвращаемого типа указан класс, то будет работать автодополнение при цепочке вызовов. @param - параметр метода/функции. Если в качестве типа параметра указан какой-либо класс, то в методе будет работать автодополнение для этого класса. @property, @property-read, @property-write - тоже самое, что и @method, только для свойства. @return - возвращаемый тип. IDE используют для автодополнения при цепочке вызовов.

Что лучше использовать if vs Switch?

Добрый вечер. Всегда было интересно что лучше использовать переключатель switch или оператор if для множества условий, в частности для каждого переборки условий. Но как это по оптимизации, как бы чтобы реализовать switch надо больше программного кода, чем для if. Кто проводил тесты подскажите пожалуйста.


Ответ

If vs. Switch Speed
По самому простому, свитч быстрее потому что эту не надо нечего решать - пришло значение - переключился на него - выполнил действие, в случае ифа - надо что-то с чем-то сравнить... =) (такое козырное объяснение на пальцах - для тех, кто будет говорить, что там только для шарпа, а в пхп все по другому =) )

Json-парсер для Delphi

Чем парсить Json? Есть какие нибудь нормальные и легкие в освоении парсеры Json?


Ответ

Все ведь на официальном сайте JSONа перечислены: JSON delphi library Delphi Web Utils json-superobject tiny-json

Почему не два алерта, а три?

Есть такая функция: Array.prototype.myFunc=function(){ ...... } И если использовать такую запись: var array = ['a', 'b']; for(var ev in array) { alert(array[ev]); } То будет не 2 алерта, а 3, т.е. первый алерт будет 'a', второй 'b', а третий 'function(){ ...... }' почему? т.е. в третем алерте будет написана функция которая создана в виде Array.prototype.myFunc=function(){ ...... }


Ответ

Потому что цикл for .. in итерирует по свойствам объекта. Из документации (перевод мой): for .. in не следует использовать для итерации по массиву, если порядок индексов важен. Индексы массива -- всего лишь перечислимые свойства с именами, являющимися целыми числами, и более ничем не отличаются от обыкновенных свойств объекта. Нет никакой гарантии, что for .. in пробежит индексы в любом ожидаемом порядке; кроме того, он пробежит все перечислимые свойства, включая не являющиеся целыми числами, а также унаследованные. Добавив myFunc, вы добавили свойство ко всем массивам. Я бы посоветовал использовать просто for (var i = 0; i < array.length; i++) { alert(array[i]); }

C, откуда 3 байта?

Вот простенький код, на экран выводит число равное 3, почему? откуда взялись эти 3 байта struct student { char name[20]; char sex; int age; float mark; };
struct student s2; int main( void ) { printf("%d", sizeof(s2) - sizeof(s2.sex) - sizeof(s2.age) - sizeof(s2.mark) -sizeof(s2.name)); // = 3 } и еще один вопрос той же темы union rec { int a[5]; struct student st; } r;
int main( void ) { printf("%d", sizeof(r) == sizeof(student) ); } почему выдает истину, если на самом деле ни какая не истина, 5 * 4 байтов разницы


Ответ

Эти три дополнительных байта - результат так называемого выравнивания. Суть его заключается в том, что данные помещаются в памяти не всегда "вплотную", вслед друг за другом, а по адресам, которые кратны размеру поля. Скажем, если int на данной платформе имеет размер 4 байта, то поле данного типа будет размещено не сразу вслед за предыдущим полем, а по ближайшему адресу, кратному четырем. Все эти хитрости с выравниванием служат одной цели - увеличению скорости работы, так как процессору проще обращаться к данным по "выровненном" адресам. Кстати, если бы ваша структура состояла только из однобайтных полей, то этого эффекта по понятным причинам бы не было По поводу второй части вопроса тоже вполне объяснимо - это вытекает из самой сущности union, который, в отличие от структур, хранит данные в одной и той же области памяти, и его размером является размер его максимального поля. Максимальным по размеру является st, следовательно sizeof(r) равен sizeof(student) По первой части вопроса почитайте тут и тут, по второй части - например, здесь Кстати: ААА, не могу понять, где лежать будут эти 20 байт???))) вот вам простая аналогия - представьте себе выключатель, которым вы включаете/выключаете свет. Вы могли бы использовать вместо одного выключателя два разных рубильника. Один - чтобы включить, а другой - чтобы выключить свет. Но удобнее иметь все это в одном выключателе. То есть когда свет включен, вы не можете его включить еще раз, когда выключен - не можете еще раз выключить. union - это нечто похожее - когда вы пользуетесь одним его полем, вы не можете пользоваться другим (точнее можете, но это не имеет смысла и приведет к ошибкам). Аналогия, конечно, кривовата, но, может, с ее помощью вам будет проще понять это

Можно ли считать HTML+CSS ООП?

Собственно вопрос в теме, добавлю скажем

,

, и т. д. - объекты #id, .class, свойства CSS - надстройки :hover, :active, :focus - события
(Не говорю про js)
Ну и вообще можно ли считать программированием или это разметка гипертекста, если так то как же конструкции типа:
CSS
.block { display: none; }
.target:hover ~ .block { display: block; {


Ответ

Извините, но это очень странное допущение. Пройдем по порядку. Не буду останавливаться на том, что ни HTML ни CSS не являются языками программирования. Ключевой сущностью в ООП является класс, представляющий собой модель некой сущности. Класс обычно помимо состояния (то есть данных, описывающих саму сущность) включает в себя и модель поведения этой сущности (это достигается наличием у класса методов, или функций класса). Так вот в случае, о котором вы говорите, модель поведения отсутствует. Далее. Как известно, основными составляющими ООП являются наследование, полиморфизм и инкапсуляция. Я с трудом себе представляю, какие механизмы в случае с HTML+CSS можно подогнать под эти три определения.Если наследование в рамках CSS еще может иметь какой-то смысл, то что понимать под полиморфизмом и инкапсуляцией? Более того, то, что вы указали в качестве якобы относящегося к ООП, к нему имеют весьма слабое отношение (за исключением такого понятия как "объект", который вы, очевидно, путаете с классом). События конкретно к ООП отношения не имеют. Свойства напрямую с ООП тоже не связаны (более того, есть ощущение, что вы путаете свойства и поля), а что более важно, не являются для самой парадигмы ООП сколько-нибудь определяющими. А вот что такое "надстройки" в контексте ООП, вообще непонятно.
C другой стороны, с помощью некоторых ухищрений можно добиться некоего подобия, но это будет больше похоже на попытку превратить собаку в человека, нежели на собственно ООП (необходимость которого в HTML+CSS очень сомнительна)

Как узнать, когда нужно удалять память?

char * buf = (char*) malloc (PWD_BUF_SIZE * sizeof (char)); buf = getcwd (buf, PWD_BUF_SIZE); ... free(buf); Удалили память, потому что выделили. char * buf = getcwd(NULL, PWD_BUF_SIZE); ... free(buf) Удалили память, но на этот раз мы не выделяли. char f[] = "/home/user/1.txt"; char * b = basename(f); ... free(b); // привело к ошибке. Почему последний вариант привел к ошибке? Чтобы лучше понять, нужно реализовать функцию basename. Как? Если представим, что внутри ее выделяется память через alloca, то внутри функции она должна была бы освободится. То есть я хочу понять, когда освобождать память, и научится создавать функции такого типа как basename, которые возвращают указатель на память, которую не нужно удалять. С первыми двумя примерами все понятно. Если мы передает NULL, то память выделяется автоматически размером PWD_BUF_SIZE.


Ответ

@andrey1, освобождать (free()) можно только ту память, которая получена в результате malloc()/calloc()/realloc() (или функций, которые возвращают результат вызова malloc/calloc/realloc). Обратите внимание, в free нельзя передавать адрес откуда-то из середины выделенного блока (только начальный адрес) и нельзя передавать его более одного раза. Конечно, я говорю о стандартной (общепринятой) их реализации. В принципе же вполне можно представить аллокатор, хранящий адреса и размеры всех выделенных блоков, (например в rb-tree), который позволяет удалять "хвосты" (и даже расщеплять ранее выделенный блок) и безболезненно реагирует на realloc/free по неправильным адресам. Расплатой за возможность таких "вольностей" будет потеря эффективности. По поводу dirname() и basename(). Думаю, тривиальный примерчик (с печатью адресов) все ставит на свои места: #include #include #include #include
int main (int ac, char *av[]) { char *s = "/usr/lib/", *p = strdup(s), *d = dirname(p), *b = basename(p); printf ("s = %p\t[%s]
" "p = %p\t[%s]
" "d = %p\t[%s]
" "b = %p\t[%s]
", s, s, p, p, d, d, b, b);
char *q = strdup(s), *n = basename(q); printf ("q = %p\t[%s]
" "n = %p\t[%s]
", q, q, n, n);
free(p); // or free(d); free(q);
return 0; } Результат запуска: avp@avp-ubu1:hashcode$ gcc c.c avp@avp-ubu1:hashcode$ ./a.out s = 0x4007d8 [/usr/lib/] p = 0x242b010 [/usr] d = 0x242b010 [/usr] b = 0x242b011 [usr] q = 0x242b030 [/usr/lib] n = 0x242b035 [lib] avp@avp-ubu1:hashcode$ Тут становится очевидно, что uname -a Linux avp-ubu1 3.13.0-34-generic #60-Ubuntu SMP Wed Aug 13 15:45:27 UTC 2014 x86_64 x86_64 x86_64 GNU/Linux эти функции меняют переданный аргумент (ставят нули) "по месту" (никакого копирования).

Анонимные функции в js - c ними или без них?

До сегодняшнего дня я считал, что js код нужно устраивать так - file.js var a = 10; // какое-то свойство
/** * Class - то, что я называю классом, * объект которого я буду создавать и * работать с его методами и свойствами. */ var Class = function(){
}; Но сегодня я увидел вариант с анонимной функцией - file.js (function(){ var a = 10;
var Class = function(){
}; }) И сразу я вспомнил, что такое исполнение уже видел, и у меня появился вопрос: а как более правильно? И в чем отличия, если они есть?


Ответ

Важно отметить, что в JavaScript`е (ECMA) не существует так называемых классов, и всякая сущность представляет собой объект. Существует 3 способа создания объектов: Используя функцию в качестве инстанции: function someFunction (prop) { this.prop = prop; ... } var object = new someFunction ('property'); Используя литеральный способ: var object = { prop: "property", } Используя анонимные функции (лямбда) var object = new function() { this.type = "property"; } Наиболее часто используется именно первый способ. Так же стоит учитывать, что в первом случае: var a = 10; // какое-то свойство var Class = function(){}; У Вас переменная "a", в глобальной области видимости, а во втором нет. Отсюда возникает идеологический вопрос в необходимости|отсутствии сокрытии данных (инкапсуляции).

Правильно ли используются принципы ООП

Имеется абстрактный класс Фигура c абстрактными методами. Его наследует абстрактный класс Фигура2D, которая определяет методы родителя. К классу Фигура2D добавлены также виртуальные методы.
Вопросы: 1) Нормально ли, что в абстрактном классе Фигура2D имеются методы с телом (методы родителя, которые нужно реализовать) 2) Нормально ли, что абстрактный класс имеет виртуальные методы (то есть класс является одновременно полиморфным и абстрактным)
p.s.: Реализуется в c#


Ответ

Да. Хотя лично я не припомню, чтобы видел иерархию наследования с двумя абстрактными классами. Вообще, чем дальше практикуешь ООП, тем больше предпочитаешь простые иерархии и композицию. Да. Абстрактный класс тем и отличается от интерфейса, что может содержать некоторое поведение по умолчанию, которое как раз и может содержаться в виртуальных методах.

Отображение двух знаков после запятой при округлении

Приветствую всех. Кто знает как сделать чтобы после округления числа типа double стояли два знака после него.
int i=3,j=7; double var, result; var = (double)(i*100)/j; result = Math.rint(100.0 * var) / 100.0; System.out.println(var); System.out.println(result);
выдает 42.857142857142854
42.86
Но если округление проходит до целого числа, например при i=1 j=4 то результатом будет 25.0. Но мне надо чтобы было 25.00. Спасибо.


Ответ

Можно воспользоваться java.util.Formatter, разделитель целой и десятичной частей зависит от java.util.Locale
System.out.println(String.format("%(.2f Default locale", var)); System.out.println(String.format(Locale.ENGLISH, "%(.2f English locale", var)); System.out.println(String.format(new Locale("ru"), "%(.2f Russian locale", var));
Выведет:
42.86 Default locale 42.86 English locale 42,86 Russian locale

Как проверить видимость элемента на странице с помощью jQuery?

jQuery позволяет изменять видимость элементов с помощью таких функций как .hide(), .show() или .toggle().
Как проверить, видим элемент или нет, с помощью jQuery?
(вопрос переведён с английского; ссылка на оригинал: Testing if something is hidden)


Ответ

У jQuery есть псевдо-селекторы :visible и :hidden. Следовательно:
if ($element.is(':visible')) { // $element виден }
if ($element.is(':hidden')) { // $element не виден }
Однако, нужно учитывать, что в большинстве случаев данные селекторы проверяют наличие или отсутствие CSS стиля display: none. Элементы со стилями visibility: hidden или opacity: 0 все равно будут считаться видимыми, поскольку визуально занимают место в теле документа.

Как задать в приложении свой шрифт?

Как добавить в приложение свой шрифт и присвоить элементу TextView?


Ответ

Краткий вариант
TextView textView = (TextView) findViewById(); Typeface typeFace = Typeface.createFromAsset(getAssets(), ""); textView.setTypeface(typeFace);
Но лучше (ну, просто кто-то любит более полные решения и не любит копировать одно и то же для всех 128 TexView в приложении) отнаследоваться от TextView:
com/example/foo/view/FontableTextView.java
public class FontableTextView extends TextView { public FontableTextView(Context context) { super(context); }
public FontableTextView(Context context, AttributeSet attrs) { super(context, attrs); UiUtil.setCustomFont(this, context, attrs, R.styleable.com_example_foo_view_FontableTextView, R.styleable.com_example_foo_view_FontableTextView_font); }
public FontableTextView(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); UiUtil.setCustomFont(this, context, attrs, R.styleable.com_example_foo_view_FontableTextView, R.styleable.com_example_foo_view_FontableTextView_font); } }
res/values/attr.xml
...
res/layuot/main_activity.xml
... ...
com/example/foo/utils/UiUtil.java
public class UiUtil {
public static final String TAG = "UiUtil";
public static void setCustomFont(View textViewOrButton, Context ctx, AttributeSet attrs, int[] attributeSet, int fontId) { TypedArray a = ctx.obtainStyledAttributes(attrs, attributeSet); String customFont = a.getString(fontId); setCustomFont(textViewOrButton, ctx, customFont); a.recycle(); }
private static boolean setCustomFont(View textView, Context ctx, String asset) { if (TextUtils.isEmpty(asset)) return false; Typeface tf = null; try { tf = getFont(ctx, asset); if (textView instanceof TextView) { ((TextView) textView).setTypeface(tf); } } catch (Exception e) { Log.e(TAG, "Could not get typeface: " + asset, e); return false; }
return true; }
private static final Hashtable> fontCache = new Hashtable>();
public static Typeface getFont(Context c, String name) { synchronized (fontCache) { if (fontCache.get(name) != null) { SoftReference ref = fontCache.get(name); if (ref.get() != null) { return ref.get(); } }
Typeface typeface = Typeface.createFromAsset( c.getAssets(), "fonts/" + name ); fontCache.put(name, new SoftReference(typeface));
return typeface; } }
}
Сам шрифт положить в assets/fonts, в частности:
assets/fonts/coolfont.ttf

Почему при использовании where результат содержит ссылку на исходный массив?

Допустим у меня есть массив List> first_mas, на котором я провожу выборку
List result = new List(); result = first_mas.Where(d => d[0] == "1").First();
Если допустим я потом в result удалю несколько элементов, то и в исходном first_mas удалятся эти элементы. Как я понимаю это из-за того что result содержит ссылку на first_mas или дело в другом? Можно как то указать чтобы результат был самостоятельным массивом (без ссылки на исходный)? Или только вручную создавать промежуточный и копировать туда?


Ответ

Where лишь фильтрует исходных список. Логично, что результат ссылается на оригинал.
Можно как то указать чтобы результат был самостоятельным массивом (без ссылки на исходный)?
Например, так:
List result = first_mas.Where(d => d[0] == "1").First().ToList();
Или:
List result = new List(first_mas.Where(d => d[0] == "1").First());

c++ тип возвращаемого значения функции

В этом примере мне нужно вернуть массив int nums[40] Как это сделать?
test() { int nums[40];
for (int i=0; i < 40; i++) { nums[i] = i + 1; }
return nums; }


Ответ

Вам надо динамически выделить память в функции и вернуть указатель на этот участок памяти:
int* test() { int *nums = new int[40]; for (int i=0; i < 40; i++) nums[i] = i + 1; return nums; }
UPD
struct int_arr_40 { int arr[40]; };
int_arr_40 test() { int_arr_40 nums; for (int i=0; i < 40; i++) nums.arr[i] = i + 1; return nums; }

Java. Обязательно ли использовать this. в коде конструктора, присваивающего значения переменным класса?

В конструкторе, предназначенном для присвоения значений переменным класса при создании объекта, иногда использую this., иногда не используют. Я проверил - оба варианта работают, является ли один из них предпочтительным?
public class Vehicle { private String color; Vehicle(String c) { color = c; } }

public class Vehicle { private String color; Vehicle(String c) { this.color = c; } }


Ответ

Необязательно, но позволяет не изобретать имена аргументам конструктора:
public class Vehicle {
private String color;
Vehicle(String color) { this.color = color; } }

Как прервать работу интерпретатора php?

Один раз я вызвал PHP без аргументов и параметров, и, как задумано разработчиками php, моя консоль стала просто не отзываться на команды: я пишу команду, а она игнорируется.
Как мне нужно было выбираться из этой ситуации?


Ответ

в случае интерпретатора php дистрибутивной сборки надо прервать его работу, нажав ctrl+c или ctrl+d

Как эмулировать нажатие на Enter на Java?

В общем, я только начинаю изучать Java и решил что уже в принципе это можно как-то использовать. Хочу попробовать написать маленькую программу, которая автоматически будет нажимать на Enter при появлении в игре кнопки принять. Объясните новичку возможно ли вообще такое осуществить на Java и с чего начать? Базовые знания уже имеются, меня бы просто направить Заранее спасибо!


Ответ

Возможно, например при помощи java.awt.Robot, он умеет:
Снимать скриншоты Манипулировать мышью и клавиатурой ... Profit!

Как перебрать элементы объекта?

Есть JSON: {"Gray":"11","Black":"18"}
Как его перебирать циклом так, чтобы можно было использовать ключ и значение? (key => value, как в цикле foreach на php)


Ответ

Данный пример: {"Gray":"11","Black":"18"}
является объектом, для обхода свойств объекта можно воспользоваться циклом for..in. При этом будут проверены все перечисляемые свойства, включая свойства предков
var o = { "Gray": "11", "Black": "18" }; for (var key in o) { console.log(key, ':', o[key]); }
Кроме того, можно воспользоваться функцией Object.keys
var o = { "Gray": "11", "Black": "18" }; Object.keys(o).forEach(function(key) { console.log(key, ':', this[key]); }, o);

Языки программирования - разница в комментах в зависимости от позиции в строке

Помогите пожалуйста с нахождением языка, на котором есть синтаксическое различие между определение коммента в начале строки и определением в середине строки ?


Ответ

VB6
В начале:
Rem я комментарий ' я тоже комментарий
А в середине - только такой
ЯКакойТоКод ' а я комментарий
Javascript, только для браузеров (ES6, Annex B)
В начале строки:
// Комментарий и это - тоже
В середине - только так:
doSmth(); // комментарий doSmthElse(); как и это НоВотТут --> СноваКод // А так - нет КакИТут // тоже можно }

Как правильно сплющить (объединить) удалённые коммиты?

Дано:
Последовательные коммиты А и В, запушенные в удалённый репозиторий.
Задача:
Сделать из них один коммит С
Вопрос:
Беглое гугленье убеждает меня в том, что достаточно что-то типа такого сделать:
git squash А git squash В git push origin branchname
Верно ли я понял и что в процессе может пойти не так?


Ответ

Шаг 0: а можно ли это делать?
что в процессе может пойти не так
Если коммиты последовательные, то конфликтов изменений не будет. Но поскольку коммиты уже отправлены на удалённый репозиторий, то вам придётся переписывать историю там и что-нибудь может пойти не так у коллег. Вот пара вопросов о том, что и когда можно ребейзить и переписывать:
В каких случаях rebase можно и нужно делать, а в каких нет? Откатить уже опубликованный коммит и опубликовать новый, не вызывая мержа у других
Кратко: никогда нельзя это делать в стабильных ветках репозитория, где кроме вас есть ещё хоть один разработчик.
Шаг 1а: сплющивание через rebase -i
Под git squash вы наверное понимаете git rebase --interactive с последующим выбором опции squash. Действительно, можно сделать так:
Ребейз к третьему коммиту с конца (пред-предпоследнему)
git rebase -i HEAD^^
откроется такой документ:
pick 7423f96 сообщение предпоследнего коммита pick 91e9b6e сообщение последнего коммита
# Rebase c9e8f38..91e9b6e onto c9e8f38 (2 commands) ...
Чтобы объединить два коммита в один нужно сделать squash последнего в предпоследний:
pick 7423f96 сообщение предпоследнего коммита squash 91e9b6e сообщение последнего коммита
А потом сохранить документ и выйти из редактора. Откроется новый документ, в котором можно написать сообщение для вновь полученного коммита. По умолчанию там будет:
# This is a combination of 2 commits. # This is the 1st commit message:
сообщение предпоследнего коммита
# This is the commit message #2:
сообщение последнего коммита
Закомментированные строки не войдут в сообщение. Если оставить пустую строку, то rebase будет прерван.
Шаг 1б: сплющивание через reset
Поскольку нужно объединить N последних коммитов, отлично подойдёт более простой способ:
# сначала очистим индекс (staging area, область подготовки коммита), # чтобы потом не закоммитить ничего лишнего git reset . # поехали git reset --soft HEAD^^
Произошло следующее:
текущая ветка переставлена на коммит HEAD^^, т.е. на два коммита назад. изменения всех коммитов вплоть до, но не включая HEAD^^ собраны в индекс
Можно сделать новый коммит:
git commit -m'message'
В отличие от способа с rebase, информация об авторе и дате оригинального коммита не сохраняется. Лучше не ребейзить таким образом чужие коммиты, т.к. информация об авторстве обычно важна.
Шаг 1в: комбинированный подход
Предположим, что в предпоследнем коммите у вас написано нормальное сообщение, раскрывающее суть изменений. А в последнем вы исправили опечатку. Т.е. было бы удобно объединить два коммита, оставив сообщение от предпоследнего.
# То же, что и в шаге 1б: собираем содержимое последнего коммита в индекс git reset . git reset --soft HEAD^
# "редактируем" последний коммит, добавляя в него содержимое индекса # (на самом деле создаём новый коммит с тем же сообщением и переставляем на него ветку) git commit --amend --no-edit
Шаг 2. запушить на удалённый репозиторий
Поскольку вы переписали свою ветку, нужно будет запушить с -f.
git push -f origin mybranch

Скорость выполнения при передаче ссылки на объект

Добрый день! Прошу Вас подсказать мне. Вопрос: какой код будет выполняться быстрее и почему? Или разницы в скорости не будет, т.к передается ссылка на область в куче.
Допустим, есть некоторый тип:
class MyClass { internal int a; public MyClass(int a) { this.a = a; } }
Вариант 1
class Program { static void Main(string[] args) { MyClass myClass = new MyClass(5); Work(myClass.a); }
static void Work(int a) { int b = a + 5; Console.WriteLine(b); } }
Вариант 2
class Program { static void Main(string[] args) { MyClass myClass = new MyClass(5); Work(myClass); }
static void Work(MyClass myClass) { int b = myClass.a + 5; Console.WriteLine(b); } }


Ответ

Все значения переменных передаются по значению:в ссылочных типах значение это ссылка, в значимых - значение.
Конкретно в вашем случае:
пример 1 Work(myClass.a); - Вы обращаетесь к куче и копируете значение из кучи, далее уже работаете с локальной переменной, которая будет храниться в стеке пример 2 Work(myClass); - Вы обращаетесь к переменной myClass и копируете ее значение, т.е. ссылку на область памяти, где хранится объект. В данном случае объектом является класс, поэтому и хранится он в куче. Далее в методе Вы обращаетесь уже к локальной переменной, хранящейся в куче, для извлечения адреса памяти и извлечения значения объекта.
На первый взгляд разница очевидна: передавать по значению проще, но представьте ситуацию, когда вам надо передать миллион значений, а использовать только 1. Тогда быстрее будет передать массив ссылок, чем массив значений.
Если посмотреть на Ваш случай, то разницы практически не видно, но первый метод будет работать быстрее.
О том, где хранятся переменные, можно прочитать здесь

Выбор неповторяющихся случайных элементов из массива

Создаем массив чисел от 1 до 75, с помощью рандома чисел от 1 до 75 начинаем поиск элемента в массиве. Совпал - удалили. Ищем дальше. Совпал - удалили. Не нашли элемент - ищем снова пока не найдем.
Вот что вышло:
int[]array; int num = (int)(Math.random()*75+1);//имитируем выпадение числа от 1 до 75 public int[] initArray(){//создаем, инициализируем и заполняем массив цифрами от 1 до 75 включительно this.array = new int[75]; for (int i = 0; i < array.length; i++){ array[i] = i+1; } return array; } public static int findNumberInMass(int[] array, int num) { for (int i = 0; i < array.length; i++) { if (num == array[i]) { return i + 1; } } return 0;//вот тут он должен не найти нужный элемент и перезапустить поиск }
Прошу помощи, а то голова кипит. Как сделать так, чтоб он находил элемент выпавший в рандоме, искал его в массиве и удалял? И чтоб он искал совпадения, а если не нашел то перезапускал рандом?


Ответ

Если я правильно понял задачу, то приведённый ниже код иллюстрирует её решение.
class Main { private final static int[] numbers = initArray();
// Заполнение массива numbers числами от 1 по 75. private static int[] initArray() { final int[] array = new int[75]; for (int i = 0; i < array.length; ++i) array[i] = i + 1; return array; }
// Поиск позиции числа n в массиве numbers. Возвращает -1, если число не найдено. private static int findNumber(final int n) { for (int i = 0; i < numbers.length; ++i) if (numbers[i] == n) return i; return -1; }
// Получение следующего случайного числа. private static int nextRandom() { while (true) { // В бесконечном цикле... final int n = (int)(Math.random()*75+1); // ... берём случайное число, ... final int pos = findNumber(n); // ... и ищем его в массиве numbers. if (pos >= 0) { // Если число найдено, ... numbers[pos] = -1; // ... то "удаляем" его... return n; // ... и завершаем цикл, ... } } // ... иначе возвращаемся к началу. }
public static void main(final String[] args) { for (int ignored : numbers) System.out.println(nextRandom()); } }
Здесь применена небольшая хитрость. Во-первых, если мы не нашли число в массиве, то возвращаем заведомо невалидный индекс (-1). А во-вторых, поскольку удаление элемента массива выполнить без создания нового массива невозможно, то во избежание этой "дорогостоящей" операции мы просто помещаем в массив на место этого числа опять-таки заведомо невалидное значение (-1).

Google Chrome: после очистки input'ы продолжают сохранять признак полей, где значения были выбраны, а не введены

Ситуация такая. Есть форма, на ней есть несколько полей, значения которых пользователь может выбрать из ранее введенных. Типичная ситуация, все браузеры такое позволяют. Однако, в Google Chrome происходит странная ситуация: после того, как форма обрабатывается скриптом и поля очищаются, у них все равно остается признак полей, которые были ранее заполнены каким-то выбранным, а не введенным значением, проще говоря - сохраняют желтый фон. Ниже поясняющая раскадровка.
Только зашли на страницу:

Заполнили поля:

Отправили:

Подскажите, как это исправить?`


Ответ

После отправки формы нужно ее сбросить методом .reset(), тогда желтый фон уберется.
document.querySelector('b').onclick = function() { // ваш код по обработке формы document.querySelector('form').reset(); } b { cursor: pointer; }

submit

В чём разница между «import java.util.*» и «import java.util.Scanner»

Вместо Scanner может быть что угодно - суть ясна. А именно: зачем использовать второй вариант, если первый и набирать короче, и пригодится когда понадобится что-то ещё из java.util? Изучаю Java и во многих примерах из книг и статьях в интернете используется второй вариант импорта, но нигде не видел объяснения почему именно так. Наверное, у него есть какие-то преимущества перед первым?


Ответ

Потому что в Java импорты нужны для разделения классов. Понятнее будет на примере. Допустим есть класс com.blabla.Scanner и вы написали import com.blabla.*;. А потом вам захотелось добавить импорт от java.util.Scanner и вы опять написали import java.util.*;. В этом случае, если вы в коде напишете Scanner, компилятор не поймет какой именно Scanner вам нужен. Полная запись импорта это не допустит
Помню, как-то добавил импорт от android.support.v7.widget.* и android.widget.*;. Когда я написал Toolbar IDE как раз и заругалась, так как он есть в обоих пакетах. Добавил к v7.widget.Toolbar и все.

Магия в Java Substring

Столкнулся со следующим непониманием, при переносе кода на c# под java. Нужно вытащить из строки символов подстроку, взять, начиная с некоторой k-й позиции n-символов. Собственно, код:
str = "((15+3)+14/2+(7*2)+3^2+(12+(7*2)))"; System.out.println(str.substring(27, 5));
Для меня, как человека немного знакомого с шарпом, код вполне понятный и логичный. В строке 33 символа, собственно, мне необходимо получить подстроку с 27 - символ ( по 32, символ ). Но в результате я получаю ошибку OutOfBoundException. Причем даже, если захочу взять с 10 позиции 3 символа. В чем может быть проблема?


Ответ

Согласно документации java, метод substring принимает 2 параметра: начальный индекс - откуда начинать вырезать, и конечный индекс - до куда вырезать.
substring(int beginIndex, int endIndex)

Как найти среднее (медиану) из трёх чисел?

Имеется три числа: 10, 20, 30. Как найти среднее из них (не самое большое и не самое маленькое), без множества условий?


Ответ

Отсортировать и взять среднее.
public static void main(String[] args) { int[] numbers = new int[] {31, 6, 13}; Arrays.sort(numbers); System.out.println(numbers[1]); }

Помогите упростить функцию

Помогите упростить функцию drawRect(int w, int h);. Понимаю, костыли за костылями, но на ошибках учатся. Мне важны какие то специальные методы для упрощения.
package com.company;
public class Main {
public static void drawRect(int w, int h) { for (int i = 0; i < w; i++) { if (i == 0) System.out.print("╔"); else if (i == (w - 1)) System.out.print("╗"); else System.out.print("═"); } System.out.print("
"); for (int i = 0; i < h; i++) {
if (i != h - 1) { System.out.print("║"); for (int j = 0; j < (w - 2); j++) { System.out.print(" "); } System.out.println("║"); } else { System.out.print("╚"); for (int j = 0; j < (w - 2); j++) { System.out.print("═"); } System.out.println("╝"); } } } public static void main(String[] args) { drawRect(30, 10); }
}
На выходе рисует
╔════════════════════════════╗ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ║ ╚════════════════════════════╝


Ответ

В примитивном виде:
public static String stringRepeat(String str, int times) { return new String(new char[times]).replace("\0", str); }
public static void drawRect(int w, int h) { System.out.print("╔"); System.out.print(stringRepeat("=", w - 2)); System.out.println("╗");
for (int i = 0; i < h - 2; i++) { System.out.print("║"); System.out.print(stringRepeat(" ", w - 2 )); System.out.println("║"); }
System.out.print("╚"); System.out.print(stringRepeat("=", w - 2)); System.out.println("╝"); }
Далее вместо множества System.out можно загонять с помощью StringBuilder в отдельную переменную и в конце вывести

Для string.repeat можно использовать apache StringUtils

Как посчитать количество вхождений символа в строку?

Есть необходимость реализовать проверку на наличие нескольких запятых в строке. Т.е. можно использовать только одну запятую.
Но в целом достаточно узнать количество вхождений символа в строку. Остальное дописать не будет проблемой.
Какие есть способы это (посчитать количество вхождений символа) сделать?


Ответ

Регулярка Использовать StringUtils.countMatches из org.apache.commons.lang3.StringUtils
int occurrence = StringUtils.countMatches("a,b,c,d", ","); System.out.println(occurrence); Использовать string.split
String string = "a,b,c,d"; String []splitArray = string.split("\\,"); System.out.println("Запятых тут : " + (splitArray.length - 1) + " штук."); String testString = "a,b,c,d"; int occurrencesCount = testString.length() - testString.replace(",", "").length(); System.out.println(occurrencesCount); Java8
String testString = "a,b,c,d"; long occurrencesCount = testString.chars().filter(ch -> ch == ',').count(); System.out.println(occurrencesCount); Еще какой-нибудь способ

UPD нашел подобную тему на enSO: How do I count the number of occurrences of a char in a String?, несколько примеров оттуда:
Spring Framework
int spring = org.springframework.util.StringUtils.countOccurrencesOf(testString, ","); System.out.println("spring = " + spring); replaceAll
int replaceAll = testString.replaceAll("[^,]", "").length(); System.out.println("replaceAll = " + replaceAll); Java8
long java8 = testString.codePoints().filter(ch -> ch == ',').count(); System.out.println("java8 = " + java8); StringTokenizer
int stringTokenizer = new StringTokenizer(" " +testString + " ", ",").countTokens()-1; System.out.println("stringTokenizer = " + stringTokenizer);
Но в данном случае надо быть осторожным, так как, например, для строки a.b.c.d этот пример будет работать, а для строки a...b.c....d или ...a.b.c.d или a....b......c.....d... и т.д. — не будет. В итоге последовательность точек между каждой из букв посчитается лишь за один символ.

Как сделать метод пригодным для with?

Есть метод-обертка для загрузки YAML в объект.
def load_yaml(path): with io.open(path, encoding='utf-8') as fp: return yaml.safe_load(fp)
Хочу использовать with с этим методом:
with load_yaml('data.yml') as data: pass
Получаю ошибку:
... with load_yaml('data.yml) as data: AttributeError: __enter__
Что я делаю не так? Какие требования предъявляются к методу, чтобы его можно было использовать с with?


Ответ

Требования предъявляются не к "методу" (у вас, кстати, это не метод, а обычная функция), а к результату, который возвращает этот "метод".
После with вообще может стоять не только вызов функции, но и абсолютно любое выражение - сначала оно будет полностью вычислено, и уже над его результатом будет совершаться with. И вот как раз к этому результату есть определённые требования.
Для того, чтобы объект можно было использовать в with, у этого объекта должны быть определены специальные методы __enter__ и __exit__. Именно в этих методах вы и объясняете интерпретатору, как он должен открыть контекст работы с этим объектом и потом безопасно закрыть его.
Более подробно вы можете нагуглить по запросу "питон контекстный менеджер" или прочитать здесь:
https://habrahabr.ru/post/186608/#context
https://habrahabr.ru/post/196382/

Как удалить повторяющиеся элементы из двумерного списка?

list = [['03:30', 70.0], ['03:30', 135.0], ['03:30', 200.0], ['03:30', 280.0], ['04:00', 360.0], ['04:00', 430.0], ['04:30', 473.0], ['04:30', 573.0]]
Как удалить элементы с одинаковым временем и оставить с большим числом, чтобы получилось:
list = [['03:30', 280.0], ['04:00', 430.0], ['04:30', 573.0]]


Ответ

In [49]: from itertools import groupby
In [50]: res = [max(g) for _,g in groupby(lst, lambda x: x[0])]
In [51]: res Out[51]: [['03:30', 280.0], ['04:00', 430.0], ['04:30', 573.0]]
можно явно указать ключ для функции max()
In [53]: res = [max(g, key=lambda x: x[1]) for _,g in groupby(lst, lambda x: x[0])]
In [54]: res Out[54]: [['03:30', 280.0], ['04:00', 430.0], ['04:30', 573.0]]
Данный код группирует список списков по первому элементу:
In [57]: for k,g in groupby(lst, lambda x: x[0]): ...: print(k, list(g)) ...: 03:30 [['03:30', 70.0], ['03:30', 135.0], ['03:30', 200.0], ['03:30', 280.0]] 04:00 [['04:00', 360.0], ['04:00', 430.0]] 04:30 [['04:30', 473.0], ['04:30', 573.0]]
после этого мы выбираем в каждой группе элемент (список) с максимальным вторым элементом:
In [58]: for k,g in groupby(lst, lambda x: x[0]): ...: print(max(g, key=lambda x: x[1])) ...: ['03:30', 280.0] ['04:00', 430.0] ['04:30', 573.0]