Страницы

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

четверг, 14 марта 2019 г.

Скрытый тулбар и ошибки binding

У меня есть следующий xaml:

and two classes as possible data context - for two different windows.
class ToolbarContextOne { public Visibility SomeProperty {get;set;} } class ToolbarContextTwo:ToolbarContextOne { public bool IsEnabled {get;set;} }
Я использую тулбар из примера в нескольких ситуациях. Для того, чтобы показывать различные данные в разных окнах, я использую разные дата контексты. Когда мне не нужна вышеупомянутая секция, я просто ставлю SomeProperty в Visibility.Collapsed. Но всё равно получаю binding error для свойства IsEnabled. Очевидно, парсер пытается выполнить все binding expressions. Есть способ заставить его не выполнять эти выражения в скрытой секции xaml?


Ответ

Наверное, более чистый путь через DataTemplate
Положите где-нибудь в ресурсы (например, глобальные, или локально в окно, или в UserControl) такое:


Ну и в том месте, где у вас был ToolbarTray, просто

При этом ContentPresenter найдёт нужный DataTemplate и использует его.

Ошибка синтаксиса при вставке данных в БД

Никак не пойму где я ошибаюсь. You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near ''persons' VALUES ('123', dfgh, kkk, 33)' at line 1
$result = mysql_query("INSERT INTO 'persons' VALUES ($idInput, $nameInput, $lnameInput, $ageInput)" , $db) or die(mysql_error());


Ответ

кавычки вокруг строковых значений кто будет проставлять? и поставьте MySQL Workbench, он автоматически подсвечивает строку с некорректным синтаксисом, в нем и дебажьте ваши запросы
p.s. и у вас еще одна ошибка (первопричина, кстати) - одинарные кавычки вокруг имени таблицы
mysql> use 'db'; #здесь корректно, но излишне, это внутренняя команда mysql # хотя use db тоже сработает (и быстрее печатать) Database changed mysql> show tables; +--------------+ | Tables_in_db | +--------------+ | OrderHistory | | users | +--------------+ 2 rows in set (0.00 sec) #здесь некорректно, не по стандарту SQL mysql> select * from 'users'; ERROR 1064 (42000): You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''users'' at line 1
во первых, в этом запросе кавычки вокруг имени таблицы не нужны, а во вторых, правильные кавычки для sql - это backticks:
mysql> select * from `users`; +----+------------+- | id | login
ответ к комменту касательно кавычек вокруг полей типа INT/DOUBLE/FLOAT и т.д.: они возможны, но не обязательны. При малой нагрузке лишний байтик потраченный на передачу кавычек незаметен.
При большой нагрузке, при вставке больших объемов данных (когда вы вставляете данные вплоть до max_allowed_packet) , когда у вас идет множество числовых полей, вы получите дополнительную нагрузку/придется снизить количество рядов, которые вы можете вставить одновременнно.
Кроме того, чисто семантически это дает понять, когда вы просматриваете какой-нибудь большой запрос, что цифры должны вставляться в колонку с числовым типом.
Когда вы видите такой запрос, вы понимаете, что в этом есть логика и намерение.

Как работает java.util.concurrent.Phaser?

Как, в данном задании, Phaser понимает, что нити являются его участниками?
Вызвав метод arriveAndAwaitAdvance(), он присоединяет нить, в которой вызван, к пасеру в состоянии прибыла на барьер?
Phaser понимает, что нити являются его участниками, за счет методов arriveAndAwaitAdvance и arrive?
Без их вызова в данной задаче он будет пустой?
package com.javarush.test.level28.lesson10.home01;
import java.util.ArrayList; import java.util.List; import java.util.concurrent.Phaser;
public class Solution { public static void main(String[] args) throws InterruptedException { List characters = new ArrayList<>(); characters.add(new Plant()); characters.add(new Plant()); characters.add(new Zombie()); characters.add(new Zombie()); characters.add(new Zombie()); start(characters); }
private static boolean isEveryoneReady = false;
private static void start(List characters) throws InterruptedException { final Phaser phaser = new Phaser(1 + characters.size());
for (final Character character : characters) { final String member = character.toString(); System.out.println(member + " присоединился к игре");
new Thread() { @Override public void run() { System.out.println(member + " готовится играть"); phaser.arriveAndAwaitAdvance(); if (!isEveryoneReady) { isEveryoneReady = true; System.out.println("Игра началась!"); } character.run(); } }.start();
}
phaser.arriveAndDeregister(); } }


Ответ

Phaser -- это разновидность барьера, аналогичен CyclicBarrier и CountDownLatch, но отличается более гибкой настройкой.
Барьер в общем виде представляет собой следующее:
задается количество потоков, которое должно собраться на барьере каждый поток, прибывающий на барьер, блокируется как только на барьере собирается заданное выше количество потоков, барьер "открывается", и все потоки продолжают свою работу
Подробнее почитать про барьеры (в т.ч. про эти три реализации) и посмотреть иллюстрацию их работы можно в статье на Хабре
В приведенном коде Phaser работает так:
инициализируется значением участников 1 + characters.size() дальше потоки в количестве characters.size() регистрируются в нем и блокируются при вызове метода arriveAndDeregister() происходит регистрация последнего участника, барьер "открывается", все потоки продолжают свою работу. При этом этот метод автоматически уменьшает количество зарегистрированных участников для следующего этапа, но в данном коде это не имеет значения.

Отвечая на конкретные вопросы:
Вызвав метод arriveAndAwaitAdvance(), он присоединяет нить, в которой вызван, к пасеру в состоянии прибыла на барьер?
Да.
Phaser понимает, что нити являются его участниками, за счет методов arriveAndAwaitAdvance и arrive?
Да.
Без их вызова в данной задаче он будет пустой?
Не совсем понятно, что вы имеете в виду. Он будет "пустой" в том смысле, что счетчик зарегистрированных участников в нем будет равен нулю.

P.S. Кстати у вас есть проблема с полем isEveryoneReady -- доступ к нему не синхронизирован и вы можете получить несколько сообщений "Игра началась!".

JS - не работает append()

Не добавляет в textarea смайлы (точнее их текстовые обозначения), в чем проблема?
В js не силен, а методом научного тыка получается или смайлы отправить, но текст не отправляется, или наоборот.
В шапке подключен jquery-1.7.1.js

  • ------------------- еще 18 смайлов ----------------


  • Ответ

    onClick="javascript: $('.textarea').val($('.textarea').val()+'::1::')"
    посмотреть, как работает

    Поиск вхождения целочисленного массива, Си

    Добрый день. Пусть имеется два массива целых чисел:
    int arr1[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9}; int arr2[] = {3, 4, 5};
    Существует ли функция (наподобие strstr для строк), которая вернет указатель, если arr2 входит в arr1, и вернет NULL, если вхождение не найдено.


    Ответ

    Набросал вариант в лоб:
    #include #include
    int find_subarray(const int *a, size_t an, const int *b, size_t bn) { for (int i = 0; i <= an - bn; i++) { if (memcmp(a + i, b, bn * sizeof(int)) == 0) return i; }
    return -1; }
    int main() { int a[] = {2, 5, 1}; int b[] = {2, 5, 1}; int pos = find_subarray(a, sizeof(a)/sizeof(int), b, sizeof(b)/sizeof(int));
    if (pos >= 0) printf("B = A[%i, %lu]
    ", pos, pos + sizeof(b)/sizeof(int)); else printf("B is not subarray of A
    ");
    return 0; }

    Почему при сортировке данных получаются числа в другом формате?

    Имеются данные которые нужно подготовить к объединению с другим блоком данных. Для этого хотелось бы хронологично упорядочить их. Пример исходных данных:
    df1
    pid syear pgsbil pgfamstd \ 0 101 1984 [3] Fachhochschulreife [1] verheiratet zus. 1 101 1985 [3] Fachhochschulreife [1] verheiratet zus. 2 101 1986 [3] Fachhochschulreife [1] verheiratet zus. ... ... ... ... 6 102 1984 [1] Hauptschulabschluss [1] verheiratet zus. 7 102 1985 [1] Hauptschulabschluss [1] verheiratet zus. ... ... ... ... 484168 31433802 2012 [2] Realschulabschluss [1] verheiratet zus. 484169 31433901 2012 [4] Abitur [2] verheiratet getr.
    Я пробовал отсортировать используя код:
    DF1 = df1.sort_values(by='syear', ascending=1)
    Но вместо года я получаю, по моему мнению, его в другой кодировке (как и всё остальное!):
    Df1 Out[53]: pid syear pgsbil pgfamstd \ 248899 320797655 -32656 81 -95 248825 891723238 -32419 43 43 250014 345587954 -32377 NaN -119 ... ... ... ... 250163 957561202 31108 -91 27 250166 449665857 31554 -1 -1
    Почему при сортировке данных получаются числа в другом формате? Как мне исправить это?


    Ответ

    похоже у вас в колонке syear или действительно отрицательные числа или, что скорее всего, большие положительные (больше 32767), которые при типе данных np.int16 превращаются в отрицательные...
    Демо:
    информация о max() и min() для типа np.int16
    In [67]: np.iinfo(np.int16) Out[67]: iinfo(min=-32768, max=32767, dtype=int16)
    как из большого положительного целого (32880) получется отрицательное (-32656) при использовании типа np.int16
    In [72]: df = pd.DataFrame({'a':[32880]}, dtype=np.int16)
    In [73]: df Out[73]: a 0 -32656
    неправильные ("плохие") года:
    In [88]: df1.query('syear <= 1980 or syear > 2016').syear Out[88]: 248737 -9076 248738 -26593 248739 1725 248740 -25171 248741 7963 248742 27137 248743 19854 248744 26738 248745 6716 248746 9885 248747 19361 248748 -19726 248749 -24605 248750 24074 248751 -8070 248752 -16027 248753 -23424 248754 3848 248755 1471 248756 30634 248757 -8162 248758 -18937 248759 16733 248760 -21923 248761 16817 248762 3834 248763 -13556 248764 -16229 248765 24272 248766 25642 ... 252510 -1 252511 -1 252512 -1 252513 -1 252514 -1 252515 -1 252516 -1 252517 -1 Name: syear, dtype: int16
    Интересное наблюдение - все "плохие" данные идут непрерывным блоком (с индексами: 248737 - 252517)

    TCP мониторинг подключения приложения

    Делаю консольное приложение, которое должно проверять подключение к определенному IP и выполнять определенные действия. Как мониторить такое подключение? Тут выводится список всех исходящих, как отфильтровать и оставить только одно?
    static void ListAvailableTCPPort(ref ArrayList usedPort) { IPGlobalProperties ipGlobalProperties = IPGlobalProperties.GetIPGlobalProperties(); TcpConnectionInformation[] tcpConnInfoArray = ipGlobalProperties.GetActiveTcpConnections(); IEnumerator myEnum = tcpConnInfoArray.GetEnumerator();
    while (myEnum.MoveNext()) { TcpConnectionInformation TCPInfo = (TcpConnectionInformation)myEnum.Current; Console.WriteLine("{0}", TCPInfo.RemoteEndPoint); usedPort.Add(TCPInfo.LocalEndPoint.Port); } }
    public static void Main() { ArrayList usedPorts = new ArrayList(); ListAvailableTCPPort(ref usedPorts); Console.ReadKey(); }


    Ответ

    Если вам необходимо проверять подключение к определенному IP-адресу,то вы должны фильтровать 1. поле RemoteEndPoint - указывает на IP-адрес и порт TCP-соединения, который вас интересует 2. У подключения должно быть состояние(State)- Established, которое означает что соединение установлено и данные могут быть отправлены.
    Вот пример кода:
    static void SearchAvailableTCPConnection(ref ArrayList usedPort, string searchAddress, int searchPort) { IPGlobalProperties ipGlobalProperties = IPGlobalProperties.GetIPGlobalProperties(); IPEndPoint filterEndpoint = new IPEndPoint(IPAddress.Parse(searchAddress), searchPort);
    TcpConnectionInformation tcpConnInfoArray = ipGlobalProperties.GetActiveTcpConnections().Where(g => g.RemoteEndPoint.Equals(filterEndpoint) && g.State ==TcpState.Established).FirstOrDefault(); if (tcpConnInfoArray != null) { Console.WriteLine("Port {0} {1} {2} ", tcpConnInfoArray.LocalEndPoint, tcpConnInfoArray.RemoteEndPoint, tcpConnInfoArray.State); } }
    private static void Main(string[] args) { ArrayList usedPorts = new ArrayList(); SearchAvailableTCPConnection(ref usedPorts, "192.168.0.2", 8090); Console.ReadKey(); }
    На экран будет выведено сообщение только в том случае, если у нас есть активное TCP-соединение с IP-адресом 192.168.0.2 по порту 8090.
    Для конвертации строки IP-адреса в класс IPAddress, используем статическую функцию этого класса Parser