Создайте общую легенду (масштаб) для 2 растров под графиками, используя научную нотацию


Я пытаюсь построить 2 растра с разными значениями с одной и той же шкалой для сравнения. Я пытался найти ответ, используя this и this.

Я сталкиваюсь с двумя проблемами:

  1. я хотел бы иметь возможность иметь метки легенды в научной нотации (слишком много десятичных знаков, чтобы быть полезным)
  2. Я бы хотел, чтобы для обоих участков была одна шкала, внизу.

Я знаком с использованием легенды(), но я не уверен, как установить положение / направление шкалы и научной нотации, используя сюжет. Я сгенерировал несколько примеров данных, чтобы показать проблему, с которой я столкнулся:

library(raster)
set.seed(10)
x = runif(2000000, -0.0005, .9875)
y = runif(2000000, -0.0008, .99)
xmat = matrix(x, nrow = 500)
ymat = matrix(x, nrow = 500)
xras = raster(xmat)
yras = raster(ymat)
min_ = min(minValue(xras), minValue(yras))
max_ = max(maxValue(xras), maxValue(yras)) 

Чтобы построить график данных, которые я использую:

par(mfrow = c(2,1))
plot( xras, col=rev( rainbow( 99, start=0,end=1 ) ), breaks=seq(min_,max_,length.out=100), legend = FALSE,  axes = FALSE )
plot( yras, col=rev( rainbow( 99, start=0,end=1 ) ), breaks=seq(min_,max_,length.out=100), legend = FALSE, axes = FALSE )
r.range = c(min_, max_)

И для создания легенды я использую:

plot(xras, legend.only=TRUE, col=rev( rainbow( 99, start=0,end=1 ) ),  legend.width=1, legend.shrink=0.75, axis.args=list(at=seq(r.range[1], r.range[2], abs(r.range[1]-r.range[2])/4), labels=seq(r.range[1], r.range[2], abs(r.range[1]-r.range[2])/4), cex.axis=0.6), legend.args=list(text='Precipitation (m)', side=1, font=2, line=2.5, cex=0.8))

Я открыт для любого метода / пакета, чтобы решить эту проблему. Я видел, что image () является популярным решением для построения растров, но предпочел бы иметь возможность сохранить проекцию, связанную с растровый.

Чтобы повторить то, на что я надеюсь: отображаются два растровых графика (которые имеют разные, но похожие значения (см. пример)), с общей легендой внизу, используя научную нотацию.

2 2

2 ответа:

Это попытка. Он будет нуждаться в большем уточнении:

library(rasterVis)
set.seed(10)
x = runif(2000000, -0.0005, .9875)
y = runif(2000000, -0.0008, .99)
xmat = matrix(x, nrow = 500)
ymat = matrix(x, nrow = 500)
xras = raster(xmat)
yras = raster(ymat)
min_ = min(minValue(xras), minValue(yras))
max_ = max(maxValue(xras), maxValue(yras))
r.range = c(min_, max_)

levelplot(stack(xras, yras), col.regions = rev(rainbow(99, start=0, end=1)), colorkey = list(space = "bottom"))

Введите описание изображения здесь

Хотя @Pascal смог ответить на этот вопрос, я обнаружил, что у меня было больше гибкости, отрабатывая свою первоначальную попытку. Хотя я сказал научную нотацию, я был неправ и просто хотел усеченные десятичные знаки, это было завершено добавлением функции round:

axis.args=list(at=seq(r.range[1], r.range[2], abs(r.range[1]-r.range[2])/4),                      labels=round(seq(r.range[1], r.range[2], abs(r.range[1]-.range[2])/4),2),  cex.axis=1),

Я смог поместить легенду под ней (и изменить внутренние и внешние поля), а также настроить настройки на ней с помощью legend.shrink, legend.width, и legend.args. В конце концов, сценарий был:

library(raster)

set.seed(10)
x = runif(2000000, -0.0005, .9875)
y = runif(2000000, -0.0008, .99)
xmat = matrix(x, nrow = 500)
ymat = matrix(x, nrow = 500)
xras = raster(xmat)
yras = raster(ymat)
min_ = min(minValue(xras), minValue(yras))
max_ = max(maxValue(xras), maxValue(yras))
op <- par(mfrow = c(2,1),
  oma = c(2,4,0,0) + 0.1,
  mar = c(5,0,1,1) + 0.1)
plot( xras, col=rev( rainbow( 99, start=0,end=1 ) ), breaks=seq(min_,max_,length.out=100), legend = FALSE,  axes = FALSE )
plot( yras, col=rev( rainbow( 99, start=0,end=1 ) ), breaks=seq(min_,max_,length.out=100), legend = FALSE, axes = FALSE )
r.range = c(min_, max_) 
plot(xras, col=rev( rainbow( 99, start=0,end=1 ) ), horizontal=TRUE, `breaks=seq(min_,max_,length.out=100), legend.only=TRUE, legend.shrink = 1, legend.width = 3, axis.args = list(at=seq(r.range[1], r.range[2], abs(r.range[1]-r.range[2])/4), labels = round(seq(r.range[1], r.range[2], abs(r.range[1]-r.range[2])/4),2),cex.axis=1), legend.args= list(text='Precipitation (XXX)', side=1, font=3, line = 2, cex=1))` 

И выглядел так: с образцом данных: Введите описание изображения здесь

И это с моими реальными данными (я изменил на axes = TRUE в командах plot() ): Введите описание изображения здесь