最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

naming - Export data from individual tiles to CSV and create unique names in gee - Stack Overflow

programmeradmin2浏览0评论

In earth engine, I divided my Image in several tiles and want to sample 500 pixels from each tile, then export the samples in separate .csv file to my drive. I don't find a solution to name the files for export in a unique way. In the code below, I created a basename ("Tile_") and unique tile indices ("indices"). However, I don't find a way to bring "Tile_" and the individual index together in the mapping process.

// sample random pixels from each tile

// Step 1: Convert the grid to a FeatureCollection
var gridFc = ee.FeatureCollection(ee.List(grid));

// Step 2: Dynamically define band names
var bandNames = ee.List.sequence(0, 20).map(function(i) {
  i = ee.Number(i).format('%d'); // Format the number as an integer (no decimal)
  return ee.List(['temperature_2m', 'precipitation', 'snowCover']).map(function(varName) {
    return ee.String(i).cat('_').cat(varName);
  });
}).flatten();

print('Dynamic Band Names:', bandNames);

// Step 4: Function to process and export each tile
// Function to process each tile and sample 500 random pixels
var processTile = function(tileFeature, index) {
  var tileGeometry = tileFeature.geometry(); // Correctly retrieve the geometry from the tile

  // Sample 500 random pixels from the tile
  var tileSamples = standImage.sample({
    region: tileGeometry,
    scale: pixelSize, // Match the pixel size of the image
    projection: crs,
    numPixels: 500, // Limit to 500 random pixels per tile
    geometries: true // Include pixel geometry for indexing
  });

  // Ensure the samples are valid before proceeding
 // tileSamples = ee.FeatureCollection(tileSamples).filter(ee.Filter.notNull(['latitude', 'longitude']));

  // Generate a description using the index for naming the export task
  var description = ee.String('Tile_Samples_').cat(ee.Number(index).format('%d')); // Correct tile name
  print(description, 'description');
  
  var bandNames = bandNames;
  print(bandnames, 'var bandnames');
  // Create the export task
  Export.table.toDrive({
    collection: tileSamples, // Collection of sampled pixels
    description: description, // Use description to set the name
    fileFormat: 'CSV', // Export as CSV
    selectors: bandNames // Use valid band names for the export
  });

  return tileFeature; // Return the tileFeature for continued processing
};

// Get the number of tiles in the grid
var numTiles = grid.size();

// Create a list of tile indices
var indices = ee.List.sequence(0, numTiles.subtract(1));

// Map the processTile function to each tile
indices.evaluate(function(indicesList) {
  indicesList.forEach(function(index) {
    var tileFeature = grid.filter(ee.Filter.eq('system:index', ee.Number(index).format('%d'))).first();
    
    // Only process if tileFeature is valid (it should have geometry)
    if (tileFeature) {
      processTile(tileFeature, index);  // Process and export each tile
    }
  });
});

This results in useless file names: "ee.String({ "type": "Invocation", "arguments": { "string1": "Tile_Samples_", "string2": { "type": "Invocation", "arguments": { "number": 0, "pattern": "%d" }, "functionName": "Number.format" } }, "functionName": "String.cat"})". Although the print log looks the way it should: "Tile_Samples_1" etc.

In earth engine, I divided my Image in several tiles and want to sample 500 pixels from each tile, then export the samples in separate .csv file to my drive. I don't find a solution to name the files for export in a unique way. In the code below, I created a basename ("Tile_") and unique tile indices ("indices"). However, I don't find a way to bring "Tile_" and the individual index together in the mapping process.

// sample random pixels from each tile

// Step 1: Convert the grid to a FeatureCollection
var gridFc = ee.FeatureCollection(ee.List(grid));

// Step 2: Dynamically define band names
var bandNames = ee.List.sequence(0, 20).map(function(i) {
  i = ee.Number(i).format('%d'); // Format the number as an integer (no decimal)
  return ee.List(['temperature_2m', 'precipitation', 'snowCover']).map(function(varName) {
    return ee.String(i).cat('_').cat(varName);
  });
}).flatten();

print('Dynamic Band Names:', bandNames);

// Step 4: Function to process and export each tile
// Function to process each tile and sample 500 random pixels
var processTile = function(tileFeature, index) {
  var tileGeometry = tileFeature.geometry(); // Correctly retrieve the geometry from the tile

  // Sample 500 random pixels from the tile
  var tileSamples = standImage.sample({
    region: tileGeometry,
    scale: pixelSize, // Match the pixel size of the image
    projection: crs,
    numPixels: 500, // Limit to 500 random pixels per tile
    geometries: true // Include pixel geometry for indexing
  });

  // Ensure the samples are valid before proceeding
 // tileSamples = ee.FeatureCollection(tileSamples).filter(ee.Filter.notNull(['latitude', 'longitude']));

  // Generate a description using the index for naming the export task
  var description = ee.String('Tile_Samples_').cat(ee.Number(index).format('%d')); // Correct tile name
  print(description, 'description');
  
  var bandNames = bandNames;
  print(bandnames, 'var bandnames');
  // Create the export task
  Export.table.toDrive({
    collection: tileSamples, // Collection of sampled pixels
    description: description, // Use description to set the name
    fileFormat: 'CSV', // Export as CSV
    selectors: bandNames // Use valid band names for the export
  });

  return tileFeature; // Return the tileFeature for continued processing
};

// Get the number of tiles in the grid
var numTiles = grid.size();

// Create a list of tile indices
var indices = ee.List.sequence(0, numTiles.subtract(1));

// Map the processTile function to each tile
indices.evaluate(function(indicesList) {
  indicesList.forEach(function(index) {
    var tileFeature = grid.filter(ee.Filter.eq('system:index', ee.Number(index).format('%d'))).first();
    
    // Only process if tileFeature is valid (it should have geometry)
    if (tileFeature) {
      processTile(tileFeature, index);  // Process and export each tile
    }
  });
});

This results in useless file names: "ee.String({ "type": "Invocation", "arguments": { "string1": "Tile_Samples_", "string2": { "type": "Invocation", "arguments": { "number": 0, "pattern": "%d" }, "functionName": "Number.format" } }, "functionName": "String.cat"})". Although the print log looks the way it should: "Tile_Samples_1" etc.

Share Improve this question edited Jan 27 at 10:25 mkrieger1 23.2k7 gold badges63 silver badges79 bronze badges asked Jan 20 at 10:28 AntonAnton 33 bronze badges
Add a comment  | 

1 Answer 1

Reset to default 0

When using the foreach javascrit method you are actually running a client side process where all the API invocation are just the json description you see as file name. the quick and dirty solution is to use getInfo() in the eport method.

Note that it's a bad way of creating a GEE query, you should rethink a bit the logic to make it work with a .map instead and run everything in one single query to GEE servers.

发布评论

评论列表(0)

  1. 暂无评论