Вы действительно могли бы сделать это, воспользовавшись вещанием .
Давайте начнем с генерации некоторого случайного числа ndarrays
указанной формы, чтобы проверить, что конечные размеры соответствуют ожидаемым:
a = np.random.rand(101, 256, 1, 3, 1, 10)
b = np.random.rand(101)
В этом случае вам придется добавить до a.ndim
размеры в b
, так что каждое значение в b
вычитается из каждого из значений в последнем измерении a
. Следуя идее этого поста, мы можем сложить до a.ndim
новых измерений более кратким способом, используя np.reshape
следующим образом:
b = b.reshape((-1,) + (1,)*(a.ndim-1))
print(b.shape)
# (101, 1, 1, 1, 1, 1)
Теперь мы могли бы вычесть b
из a
как требуется, выполнив:
a[..., 0, None] = a[..., 0, None] - b.reshape((-1,) + (1,) * (a.ndim-1))
И если мы проверим форму a
:
print(a.shape)
# (101, 256, 1, 3, 1, 10)
]
Вот некоторые пояснения по некоторым вопросам, которые могут возникнуть из предыдущего ответа. Давайте рассмотрим следующий более простой пример:
a = np.array([[1,2,3],[4,5,6]])
print(a)
array([[1, 2, 3],
[4, 5, 6]])
print(a.shape)
# (2, 3)
b = np.array([1,1])[:,None]
array([[1],
[1]])
print(b.shape)
# (2, 1)
Таким образом, для этого примера мы могли бы применить ту же логику, что и решение, приведенное выше:
a[:,0,None] = a[:,0,None] - b
array([[0, 2, 3],
[3, 5, 6]])
Который, проверяя полученный массив, как Ожидаемый b
был вычтен из a
по первому указателю вдоль его последней оси, поэтому первый столбец во всех строках.
Итак, первая точка,
Почему мы должны добавить новую ось в
blockquote>a
для вычитания?Необходимо добавить новая ось
a
, имеющая формуb
. Обратите внимание, чтоb
является двумерным массивомarray([[1],[1]])
, поэтому, если бы вы вычли его непосредственно изa
, вы бы получили:a[..., 0] - b array([[0, 3], [0, 3]])
Итак, здесь произошло то, что Массив меньшего размера, т. е. первый член, представляющий собой просто срез вида
1D
изa
,array([1, 4])
, транслировался по большому массиву, чтобы они имели совместимые формы.В этом не было бы необходимости, если бы форма
b
была вместо(2,)
:b = np.array([1,1]) a[:,0] - b # array([0, 3])
Но из-за того, как
b
было определено фактическое решение, оно имеет столько же размеров, что и вa
. Таким образом, чтобы получить правильный вывод, мы должны добавить новую ось кa
:a[:,0,None] - b array([[0], [3]])
Таким образом, мы получим правильный вывод.
При использовании описанного выше метода не представляется возможным присвоить разницу новому массиву, выступающему в качестве «исправленной копии»?
blockquote>Ответ на этот вопрос можно понять, взглянув на результат вычитания:
c = a[:,0,None] - b c.shape (2, 1)
Итак, здесь
a[:,0,None]
есть то, что называется «разрезанным видом» изa
. Итак, обратите внимание, что, присваивая этот результатc
, вы сохраняете только фактическоеsliced wiew
изa
, а не весьndarray
. Если вы хотите изменитьa
в тех же позициях фактического среза, вам нужно будет присвоить его тому же срезанному представлениюa
, поэтому:a[:,0,None] = a[:,0,None] - b print(a.shape) # (2, 3)
Теперь результат имеет ожидаемый результат, так как мы только изменили срез
a
. Если вы хотите сохранить копию оригиналаndarray
, вы можете использоватьnp.copy
, который будет возвращать фактическую копию, а не фрагментa
, а затем назначать результат для " исправленная копия ":a_c = np.copy(a) a_c[:,0,None] = a[:,0,None] - b
Linking statically will bloat all your EXEs and DLLs, and can cause crashes (eg. if code in one DLL calls free() with a pointer allocated by malloc() in a different DLL).
You can get the best of both worlds by linking dynamically and deploying the runtime DLLs as private assemblies. This simply means putting a copy of a specially-named directory containing the runtime DLLs and their manifests next to your executable.
See the section "Deploying Visual C++ library DLLs as private assemblies" at http://msdn.microsoft.com/en-us/library/ms235291(VS.80).aspx for details, but basically your application looks like this:
c:\Program Files\My App\MyApp.exe
c:\Program Files\My App\MyLibrary.dll
c:\Program Files\My App\Microsoft.VC80.CRT\Microsoft.VC80.CRT.manifest
c:\Program Files\My App\Microsoft.VC80.CRT\msvcr80.dll
As to your last question, yes, the target machine needs the correct versions of the runtime DLLs to work, but by deploying them as private assemblies, you guarantee that.
Another benefit is that non-admin users can install your app (not into Program Files, but elsewhere) - they don't need permission to write files into the WinSxS area.
Единственный раз, когда вы получите несколько копий среды выполнения, - это когда вы статически связываете библиотеку с DLL - каждая DLL получит копию, как и исполняемый файл. Если они все статические библиотеки, а не библиотеки DLL, они все будут связаны друг с другом, и все ваши библиотеки будут использовать одну и ту же среду выполнения.
Это работа компоновщика.
... Делать это статически ... попытки исправить DLL Ад не сработали так хорошо ... просто добавьте дополнительные 200 КБ к вашей установке со статической связью.
Статические библиотеки не нужно статически связывать с другими статическими библиотеками. Вам нужно только связать все статические библиотеки в вашем основном проекте. Таким образом, компилятор не будет жаловаться на несколько символов.