Вы можете сделать левое соединение между двумя кадрами данных следующим образом:
import org.apache.spark.sql.functions.when
import spark.implicits._
val df1 = sc.parallelize(Seq((2,3),(1,4))).toDF("id1","id2")
val df2 = sc.parallelize(Seq((4,1),(2,3))).toDF("id1","id2")
val df3 = df1.join(df2, df1("id1")===df2("id1") && df1("id2") === df2("id2"), "left")
.select(df1("id1"),
df1("id2"),
when(df2("id1").isNull, 0).otherwise(1).alias("label"))
df3.show()
+---+---+-----+
|id1|id2|label|
+---+---+-----+
| 2| 3| 1|
| 1| 4| 0|
+---+---+-----+
Надеюсь, это поможет вам.
У Вас есть ошибка. Вместо:
translatedArray=malloc(4*sizeof(short int));
Вы должны иметь
translatedArray=malloc(4*sizeof(short int*));
Отметьте недостающий указатель в своем коде. Я подозреваю, что это - то, где Ваше наблюдаемое поведение происходит от.
Также заметьте это 0x804a420 - 0x804a018 = 1032
, нет 516
. Формула translatedArray[i] - translatedArray[i - 1]
дает Вам число элементов (короткие целые, или проще, короткие замыкания) промежуточный два адреса, не число байтов.
Во-первых, Malloc не делает гарантий, что два последовательных вызова malloc возвращают последовательные указатели.
Второй, в зависимости от Вашей определенной архитектуры, различные правила выравнивания применяются; иногда Вы могли бы попросить единственный байт, но архитектура предпочитает выделения на 8-или 4-байтовые интервалы.
В-третьих, malloc нужны немного служебные, чтобы сохранить, насколько большой выделенный блок и т.д.
Не делайте предположения о том, какой malloc делает мимо, что говорит документация!
malloc
функция всегда выделяет немного больше, чем Вы просите, чтобы хранить некоторую бухгалтерскую информацию. В конце концов, когда Вы звоните free()
это должно знать, насколько большой блок.
Кроме того, обычно malloc
реализации будут вокруг требуемого размера до следующего несколько из 8 или 16 или некоторое другое кругловатое число.
Обновление: реальный ответ на Ваш вопрос заключается в Вашем использовании short int
ввести. Когда выполнение адресной арифметики с указателями (вычитание) между введенными указателями, C и C++ возвращается, различие в количестве вещей указало. Так как Вы указываете short int
, который составляет два байта в размере, возвращенное значение является половиной того, что Вы ожидаете.
С другой стороны, malloc
всегда выделяет данное число байтов, к независимо от того, чему Вы бросаете результат позже. Попробуйте это:
array=(short int*)malloc(sizeof(short int) * size);
Нет никаких гарантий что два блока возврата вызовов malloc, точно упакованные вместе - на самом деле нет никаких гарантий о результате вообще, за исключением того, что, если это не является ПУСТЫМ, он укажет на блок как наименьшее количество целый тот, который требуют.
Внутренне, большинство mallocs содержит рабочие данные, чтобы помочь им управлять "кучей". Например, те 8 байтов могли бы содержать два указателя - один указывающий на следующий блок, и один указывающий на предыдущий блок. Я не знаю то, что - те 8 байтов то, потому что Вы не упоминали, на котором ОС Вы работаете, но совершенно нормально для malloc использовать некоторую память для себя негласно.
Некоторые средства выделения (например, на окнах) обеспечивают библиотечную функцию для обнаружения размера блока, данного подсказка, однако, некоторые не делают, поскольку это - довольно тайная функция.
Какие возвраты malloc зависит от реализации malloc и архитектуры. Как другие уже сказали, Вы, как гарантируют, получите, ПО КРАЙНЕЙ МЕРЕ, требуемый объем памяти или ПУСТОЙ УКАЗАТЕЛЬ. Это также, почему иногда, можно записать мимо конца массива и не получить отказ сегментации. Это - потому что у Вас на самом деле есть допустимый доступ к этой памяти, Вы просто не знали это.
malloc () обычно реализуется путем разделения доступной "кучи" в блоках различных размеров. В Вашем случае, malloc () возвращает 2 последовательных 1024 (или 16) блоки байта. 8 байтов пространства, которое Вы упоминаете, используются malloc () для бухгалтерской информации.
Посмотрите malloc Doug Lea () impl примечания здесь для понимания то, что входит негласно: http://g.oswego.edu/dl/html/malloc.html
malloc()
будет иметь свои собственные издержки.
Не говоря уже о том, что нет никакой гарантии, что 2 последовательных выделения будут друг рядом с другом для начала.
Я нашел это ... и проверил ссылку ниже для получения дополнительной информации.
Блок выделяется из свободного пула путем предварительного преобразования запрошенных байтов в индекс в массиве сегментов, используя следующее уравнение:
required = требуемый + 8
при необходимости <= 16, тогда ведро = 0
При необходимости> 16, тогда bucket = (log (необходимо) / log (2) округлено до ближайшего целого числа) - 3
Размер каждого блока в списке, привязанного к сегменту, равен size block = 2 bucket + 4. Если список в bucket равен нулю, память выделяется с помощью подпрограммы sbrk для добавления блоков в список. Если размер блока меньше, чем страница, то страница выделяется с помощью подпрограммы sbrk, и число блоков, полученных путем деления размера блока на размер страницы, добавляется в список. Если размер блока равен или превышает страницу, необходимая память выделяется с помощью подпрограммы sbrk, и в свободный список для блока добавляется один блок. Если свободный список не пуст, блок в начале списка возвращается вызывающей стороне. Следующий блок в списке становится новым главой.
Если malloc
возвраты что-либо кроме пустого указателя, затем память, что это было выделено для Вашей программы, имеет размер, которому Вы передали malloc
. Взятие различия в указателе между возвращаемыми значениями двух вызовов различия к malloc
мог иметь любое значение и ничего не имеет (хорошо мало), чтобы сделать с размером блока первого выделенного блока.
Прежде чем указатель стоит размер следующего массива, который является целым числом на 32/64 бита (не знайте, если подписано или неподписанный),