Related
Firstly, i should mention that i only recently started programming (about a year ago). My main-language is Java.
to elaborate on what I've done:
to learn about Neural Networks i watched 3Blue1Brown´s series on the topic
after (mostly) understanding it i started to make the actual Implementation
I implemented a File-Reader to turn the raw numbers of the Database (i used MNIST just like 3b1b) into three arrays : 1 for the labels, 1 for the Images and one for the grayscale-values (i mapped the RGB values between 0 and 1) in one input-array
I then designed a test() and train() method, this is what i did:
public class Network {
int L;
int[] Lsize;
double[][][] weights;
double[][] biases;
public Network(int... Lsize) {
L = Lsize.length;
this.Lsize = Lsize;
weights = new double[L - 1][][];
for (int i = 0; i < L - 1; i++) {
weights[i] = new double[Lsize[i + 1]][Lsize[i]];
for (int j = 0; j < Lsize[i + 1]; j++) {
for (int k = 0; k < Lsize[i]; k++) {
weights[i][j][k] = (Math.random() * 2) - 1;
}
}
}
biases = new double[L - 1][];
for (int i = 0; i < L - 1; i++) {
biases[i] = new double[Lsize[i + 1]];
for (int j = 0; j < Lsize[i + 1]; j++) {
biases[i][j] = (Math.random() * 2) - 1;
}
}
}
public static void main(String[] args) {
Network n = new Network(28 * 28, 16, 16, 10);
Database mnist_train = new Database(60000, 28, 28, "mnist_train");
Database mnist_test = new Database(10000, 28, 28, "mnist_test");
System.out.println("accuracy= " + n.accuracy(mnist_test));
for(int i = 0; i < 50; i ++) {
n.train(mnist_train, 10, 0.1);
System.out.println("accuracy= " + n.accuracy(mnist_test));
}
}
public void train(Database data,int batchsize,double factor) {
Batch[] batches = data.dividetoBatches(batchsize);
for (int b = 0; b < data.n / batchsize; b++) {
System.out.println("Step " + b + " started!");
Batch batch = batches[b];
double[][][] averagegweights = new double[L - 1][][];
double[][] averagegbiases = new double[L - 1][];
for (int i = 0; i < L - 1; i++) {
averagegweights[i] = new double[Lsize[i + 1]][Lsize[i]];
averagegbiases[i] = new double[Lsize[i + 1]];
}
double averagecost = 0;
for (int e = 0; e < batchsize; e++) {
double[] target = batch.target[e];
double[] values = batch.values[e];
double[][] z = new double[L - 1][];
double[][] a = new double[L][];
a[0] = values;
for (int i = 0; i < L - 1; i++) {
a[i + 1] = new double[Lsize[i + 1]];
z[i] = new double[Lsize[i + 1]];
for (int j = 0; j < Lsize[i + 1]; j++) {
double sum = biases[i][j];
for (int k = 0; k < Lsize[i]; k++) {
sum += weights[i][j][k] * a[i + 1][j];
}
z[i][j] = sum;
a[i + 1][j] = sigmoid(sum);
}
}
double[][][] gweights = new double[L - 1][][];
double[][] gbiases = new double[L - 1][];
double[][] dCa = new double[L][];
double cost = 0;
dCa[L - 1] = new double[Lsize[L - 1]];
for (int i = 0; i < Lsize[L - 1]; i++) {
dCa[L-1][i] = 2 * (target[i] - a[L - 1][i]);
cost += (target[i] - a[L - 1][i]) * (target[i] - a[L - 1][i]);
}
// Backpropagation:
for (int i = L - 2; i >= 0; i--) {
dCa[i] = new double[Lsize[i]];
gweights[i] = new double[Lsize[i+1]][Lsize[i]];
gbiases[i] = new double[Lsize[i]];
for (int j = 0; j < Lsize[i + 1]; j++) {
gbiases[i][j] = dsigmoid(z[i][j]) * dCa[i+1][j];
for (int k = 0; k < Lsize[i]; k++) {
gweights[i][j][k] = a[i][k] * dsigmoid(z[i][j]) * dCa[i+1][j];
}
}
for (int k = 0; k < Lsize[i]; k++) {
dCa[i][k] = 0;
for (int j = 0; j < Lsize[i + 1]; j++) {
dCa[i][k] += weights[i][j][k] * dsigmoid(z[i][j]) * dCa[i + 1][j];
}
}
}
for (int i = 0; i < L - 1; i++) {
for (int j = 0; j < Lsize[i + 1]; j++) {
averagegbiases[i][j] += gbiases[i][j];
for (int k = 0; k < Lsize[i]; k++) {
averagegweights[i][j][k] += gweights[i][j][k];
}
}
}
averagecost += cost;
}
for (int i = 0; i < L - 1; i++) {
for (int j = 0; j < Lsize[i + 1]; j++) {
averagegbiases[i][j] = averagegbiases[i][j]/batchsize * -1;
for (int k = 0; k < Lsize[i]; k++) {
averagegweights[i][j][k] = averagegweights[i][j][k]/batchsize * -1;
}
}
}
for (int i = 0; i < L - 1; i++) {
for (int j = 0; j < Lsize[i + 1]; j++) {
biases[i][j] += averagegbiases[i][j] * factor;
for (int k = 0; k < Lsize[i]; k++) {
weights[i][j][k] += averagegweights[i][j][k] * factor;
}
}
}
averagecost = averagecost/batchsize;
System.out.println("averagecost = " + averagecost);
// System.out.println(Arrays.deepToString(batch.target));
System.out.println("Das sollte eine" + data.labels[0] + " sein!");
data.shuffle();
double[] output = test(data.values[0]);
for (int i = 0; i < output.length; i++) {
float val = (float) output[i];
System.out.print(i + ": ");
System.out.printf("%.2f", val);
System.out.println();
}
System.out.println("Step " + b + " finished!");
}
}
public double accuracy(Database data) {
int rightanswers = 0;
int answers = 0;
for(int i = 0; i < data.n; i++) {
if(maxIndex(test(data.values[i])) == data.labels[i]) {
rightanswers++;
}
answers++;
}
return (double)rightanswers/(double)answers;
}
public int maxIndex(double[] output) {
int index = 0;
for(int i = 0; i < output.length; i++) {
if(output[i] > output[index])
index = i;
}
return index;
}
public double[] test(double[] input) {
double[][] values = new double[L][];
values[0] = input;
for (int i = 0; i < L - 1; i++) {
values[i + 1] = new double[Lsize[i + 1]];
for (int j = 0; j < Lsize[i + 1]; j++) {
double sum = biases[i][j];
for (int k = 0; k < Lsize[i]; k++) {
sum += weights[i][j][k] * values[i][k];
}
values[i + 1][j] = sigmoid(sum);
}
}
double[] output = values[L - 1];
return output;
}
public double sigmoid(double x) {
return 1 / (1 + Math.pow(Math.E, x));
}
// derivative of the sigmoid-function
public double dsigmoid(double x) {
return sigmoid(x) * (1 - sigmoid(x));
}
}
my problem now is when i run the training the Cost-function decreases, but only because all of the output-values are nearing 0 and not because the network has actually found the right number to the picture.
after about one run through the Database the average Cost stagnates around 0.9
am i missing something fundamental or am i just not noticing an simple error
Thank you in advance
I`m sorry for my bad English, I´m actually German
The first thing you can do is to increase the complexity of the network. I just tried your architecture with my implementation and the network you currently have definitely isn't big enough to fit handwritten digits. I would recommend 784,128,128,10 as that had around 90% accuracy for 3 runs over the training set. If that doesn't yield better results, make sure your implementation of a neural network is functional on something less complex like the XOR problem. If XOR is learnable by your implementation, it could be the way you are altering the dataset. Debugging a neural network is tough, but you have to make sure the foundation of it is built correctly before looking at higher-level problems like learning rate and optimizers. You're using vanilla gradient descent so you should definitely implement momentum as it is easier to implement than what you've already done and is a significant improvement to your current method.
for one of my assignments I am required to print out stars in the shape of a diamond. When trying to print odd numbers, everything works out fine. However, when trying to print even numbered diamonds, the spacing in the middle lines is off, and a diamond is missing. Could someone please point out what I am doing wrong, and provide a possible fix?
public void printStarsDiamond(int d)
{
for (int i = 1; i < d; i = i + 2)
{
for (int j = 0; j < (d - i) / 2; j++)
{
System.out.print(" ");
}
for (int k = 0; k < i; k++)
{
System.out.print("*");
}
System.out.println();
}
for (int i = d; i > 0; i = i - 2)
{
for (int j = 0; j < (d - i) / 2; j++)
{
System.out.print(" ");
}
for (int k = 1; k <= i; k++)
{
System.out.print("*");
}
System.out.println();
}
Desired result, if the user enters 6 (d = 6)
If you notice your code, the second for loop is starting from
i = d in
for (int i = d; i > 0; i = i - 2)
but your first loop is not ending at d, you are doing i < d there which will stop before d, so it will go from 1 to 5 if your d value is 6.
Simply change your second main for loop to start from d-1, here is the code
public void printStarsDiamond(int d)
{
for (int i = 1; i < d; i = i + 2)
{
for (int j = 0; j < (d - i) / 2; j++)
{
System.out.print(" ");
}
for (int k = 0; k < i; k++)
{
System.out.print("*");
}
System.out.println();
}
for (int i = d-1; i > 0; i = i - 2)
{
for (int j = 0; j < (d - i) / 2; j++)
{
System.out.print(" ");
}
for (int k = 1; k <= i; k++)
{
System.out.print("*");
}
System.out.println();
}
The code below will print a diamond pattern using a single loop:
private static void PrintDiamondSingleLoop(int row) {
row++;
int mid = row/2;
int midLeft = mid;
int midRight = mid;
int currentRow = 1;
int currentColumn = 1;
for (int i = 1; i <= row * row; i++)
{
if(i % row == 0)
{
System.out.println("");
if(currentRow < mid)
{
midLeft--;
midRight++;
}else
{
midLeft++;
midRight--;
}
currentColumn = 1;
currentRow++;
}
if (currentColumn >= midLeft && currentColumn <= midRight)
{
System.out.print("*");
}
else
{
System.out.print(" ");
}
currentColumn++;
}
}
(This code is taken from an article published on my website: https://programtown.com/how-to-print-diamond-pattern-using-single-for-loop-in-java/.)
I am working on a problem where I've to print the largest sum among all the hourglasses in the array. You can find the details about the problem here-
What I tried:
public class Solution {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int arr[][] = new int[6][6];
for (int arr_i = 0; arr_i < 6; arr_i++) {
for (int arr_j = 0; arr_j < 6; arr_j++) {
arr[arr_i][arr_j] = in.nextInt();
}
}
int sum = 0;
int tmp_sum = 0;
for (int arr_i = 0; arr_i < 4; arr_i++) {
for (int arr_j = 0; arr_j < 4; arr_j++) {
if (arr[arr_i][arr_j] > 0) {
sum = sum + (arr[arr_i][arr_j]) + (arr[arr_i][arr_j + 1]) + (arr[arr_i][arr_j + 2]);
sum = sum + (arr[arr_i + 1][arr_j + 1]);
sum = sum + (arr[arr_i + 2][arr_j]) + (arr[arr_i + 2][arr_j + 1]) + (arr[arr_i + 2][arr_j + 2]);
if (tmp_sum < sum) {
tmp_sum = sum;
}
sum = 0;
}
}
}
System.out.println(tmp_sum);
}
}
Input:
1 1 1 0 0 0
0 1 0 0 0 0
1 1 1 0 0 0
0 9 2 -4 -4 0
0 0 0 -2 0 0
0 0 -1 -2 -4 0
Output:
12
Expected Output:
13
Screenshot:
I don't know where I'm doing wrong. I cannot understand why the expected output is 13. According to the description given in the problem it should be 10. Is this a wrong question or my understanding about this is wrong?
Remove the if (arr[arr_i][arr_j] > 0) statement. It prevents finding the answer at row 1, column 0, because that cell is 0.
Comments for other improvements to your code:
What if the best hourglass sum is -4? You should initialize tmp_sum to Integer.MIN_VALUE. And name it maxSum, to better describe it's purpose.
You shouldn't define sum outside the loop. Declare it when it is first assigned, then you don't have to reset it to 0 afterwards.
Your iterators should be just i and j. Those are standard names for integer iterators, and keeps code ... cleaner.
If you prefer longer names, use row and col, since that is what they represent.
You don't need parenthesis around the array lookups.
For clarity, I formatted the code below to show the hourglass shape in the array lookups.
Scanner in = new Scanner(System.in);
int arr[][] = new int[6][6];
for (int i = 0; i < 6; i++){
for (int j = 0; j < 6; j++){
arr[i][j] = in.nextInt();
}
}
int maxSum = Integer.MIN_VALUE;
for (int i = 0; i < 4; i++) {
for (int j = 0; j < 4; j++) {
int sum = arr[i ][j] + arr[i ][j + 1] + arr[i ][j + 2]
+ arr[i + 1][j + 1]
+ arr[i + 2][j] + arr[i + 2][j + 1] + arr[i + 2][j + 2];
if (maxSum < sum) {
maxSum = sum;
}
}
}
System.out.println(maxSum);
This was my solution. I wrapped an if statement around the code that calculates the sum, that makes sure we don't go out of bounds.
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int arr[][] = new int[6][6];
int max = Integer.MIN_VALUE;
int tempMax = 0;
for(int i=0; i < 6; i++){
for(int j=0; j < 6; j++){
arr[i][j] = in.nextInt();
}
}
for(int i=0; i < 6; i++){
for(int j=0; j < 6; j++){
if (i + 2 < 6 && j + 2 < 6) {
tempMax += arr[i][j] + arr[i][j + 1] + arr[i][j + 2];
tempMax += arr[i + 1][j + 1];
tempMax += arr[i + 2][j] + arr[i + 2][j + 1] + arr[i + 2][j + 2];
if (max < tempMax) {
max = tempMax;
}
tempMax = 0;
}
}
}
System.out.println(max);
}
Here's the simple and easy to understand C# equivalent code for your hourglass problem.
class Class1
{
static int[][] CreateHourGlassForIndex(int p, int q, int[][] arr)
{
int[][] hourGlass = new int[3][];
int x = 0, y = 0;
for (int i = p; i <= p + 2; i++)
{
hourGlass[x] = new int[3];
int[] temp = new int[3];
int k = 0;
for (int j = q; j <= q + 2; j++)
{
temp[k] = arr[i][j];
k++;
}
hourGlass[x] = temp;
x++;
}
return hourGlass;
}
static int findSumOfEachHourGlass(int[][] arr)
{
int sum = 0;
for (int i = 0; i < arr.Length; i++)
{
for (int j = 0; j < arr.Length; j++)
{
if (!((i == 1 && j == 0) || (i == 1 && j == 2)))
sum += arr[i][j];
}
}
return sum;
}
static void Main(string[] args)
{
int[][] arr = new int[6][];
for (int arr_i = 0; arr_i < 6; arr_i++)
{
string[] arr_temp = Console.ReadLine().Split(' ');
arr[arr_i] = Array.ConvertAll(arr_temp, Int32.Parse);
}
int[] sum = new int[16];
int k = 0;
for (int i = 0; i < 4; i++)
{
for (int j = 0; j < 4; j++)
{
int[][] hourGlass = CreateHourGlassForIndex(i, j, arr);
sum[k] = findSumOfEachHourGlass(hourGlass);
k++;
}
}
//max in sum array
Console.WriteLine(sum.Max());
}
}
Happy Coding.
Thanks,
Ankit Bajpai
You can try this code:
I think this will be easy to understand for beginners.
public class Solution {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int arr[][] = new int[6][6];
for(int arr_i=0; arr_i < 6; arr_i++){
for(int arr_j=0; arr_j < 6; arr_j++){
arr[arr_i][arr_j] = in.nextInt();
}
}
int sum = 0;
int sum2 = 0;
int sum3 = 0;
int x = 0;
int max = Integer.MIN_VALUE;
for(int i = 0; i < 4; i++){
for(int j = 0; j < 4; j++){
for(int k = 0; k < 3; k++){
sum += arr[i][j+k]; //top elements of hour glass
sum2 += arr[i+2][j+k]; //bottom elements of hour glass
sum3 = arr[i+1][j+1]; //middle elements of hour glass
x = sum + sum2 + sum3; //add all elements of hour glass
}
if(max < x){
max = x;
}
sum = 0;
sum2 = 0;
sum3 = 0;
x = 0;
}
}
System.out.println(max);
}
}
Here is another easy option, hope it helps:
import java.io.*;
import java.util.*;
import java.text.*;
import java.math.*;
import java.util.regex.*;
public class Solution {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int a[][] = new int[6][6];
for(int i=0; i < 6; i++){
for(int j=0; j < 6; j++){
a[i][j] = in.nextInt();
}
}
int hg = Integer.MIN_VALUE, sum;
for(int i=0; i<4; i++){
for(int j=0; j<4; j++){
sum = 0;
sum = sum + a[i][j] + a[i][j+1] + a[i][j+2];
sum = sum + a[i+1][j+1];
sum = sum + a[i+2][j] + a[i+2][j+1] + a[i+2][j+2];
if(sum>hg)
hg = sum;
}
}
System.out.println(hg);
in.close();
}
}
there is another opetion in case of -(minus) and zero output we can use shorted ser Treeset for the same . below is the sameple code
public class Solution {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int arr[][] = new int[6][6];
for(int i=0; i < 6; i++){
for(int j=0; j < 6; j++){
arr[i][j] = in.nextInt();
}
}
int sum=0;int output=0;
Set<Integer> set=new TreeSet<Integer>();
for(int k=0;k<4;k++ )
{
for(int y=0;y<4;y++)
{
sum=arr[k][y]+arr[k][y+1]+arr[k][y+2]+arr[k+1][y+1]+arr[k+2][y]+arr[k+2][y+1]+arr[k+2][y+2]; set.add(sum);
}
}
int p=0;
for(int u:set)
{
p++;
if(p==set.size())
output=u;
}
System.out.println(output);
}
}
Solved in PHP, may be helpful.
<?php
$handle = fopen ("php://stdin","r");
$input = [];
while(!feof($handle))
{
$temp = fgets($handle);
$input[] = explode(" ",$temp);
}
$maxSum = PHP_INT_MIN;
for($i=0; $i<4; $i++)
{
for($j=0; $j<4; $j++)
{
$sum = $input[$i][$j] + $input[$i][$j + 1] + $input[$i][$j + 2]
+ $input[$i + 1][$j + 1] +
$input[$i + 2][$j] + $input[$i + 2][$j + 1] + $input[$i + 2][$j + 2];
if($sum > $maxSum)
{
$maxSum = $sum;
}
}
}
echo $maxSum;
?>
Passes all test cases
import java.io.*;
import java.util.*;
public class Solution {
public static void main(String[] args) {
Scanner read = new Scanner(System.in);
int rowSize = 6;
int colSize = 6;
int[][] array = new int[rowSize][colSize];
for(int row = 0; row < rowSize; row++) {
for(int col = 0; col < colSize; col++) {
array[row][col] = read.nextInt();
}
}
read.close();
int max = Integer.MIN_VALUE;
for(int row = 0; row < 4; row++) {
for(int col = 0; col < 4; col++) {
int sum = calculateHourglassSum(array, row, col);
if(sum > max) {
max = sum;
}
}
}
System.out.println(max);
}
private static int calculateHourglassSum(int[][] array, int rowIndex, int colIndex) {
int sum = 0;
for(int row = rowIndex; row < rowIndex + 3; row++) {
for(int col = colIndex; col < colIndex + 3; col++) {
if(row == rowIndex + 1 && col != colIndex + 1) {
continue;
}
sum += array[row][col];
}
}
return sum;
}
}
function galssSum(array) {
let maxGlass = 0;
if (array[0].length == 3) {
maxGlass = 1;
} else if (array[0].length > 3) {
maxGlass = array.length - 2;
}
let maxValue = -100000;
for (let i = 0; i < maxGlass; i++) {
for (let j = 0; j < maxGlass; j++) {
let a = array[i][j] + array[i][j + 1] + array[i][j + 2];
let b = array[i + 1][j + 1];
let c = array[i + 2][j] + array[i + 2][j + 1] + array[i + 2][j + 2];
let sum = a + b + c;
if (maxValue<sum) {
maxValue = sum;
}
}
}
return maxValue;
}
console.log(galssSum([[1, 1, 1, 0, 0, 0], [0, 1, 0, 0, 0, 0], [1, 1, 1, 0, 0, 0], [0, 0, 2, 4, 4, 0], [0, 0, 0, 2, 0, 0], [0, 0, 1, 2, 4, 0]]));
int hourglassSum(vector<vector<int>> vec) {
int res = 0;
int size = ((vec[0].size())-2) * ((vec.size())-2);
//cout<<size<<endl;
vector<int> res_vec(size);
int j = 0;
int itr =0 ;
int cnt = 0;
int mid = 0;
int l =0;
while((l+2) < vec.size())
{
while((j+2) < vec.size())
{
for(int i =j ;i<j+3; i+=2)
{
//cout<<i<<" :";
for(int k=l;k<l+3;k++)
{
//cout<<k<<" ";
res_vec[itr] += vec[i][k];
}
//cout<<endl;
}
res_vec[itr] += vec[j+1][l+1];
//cout<<endl;
itr++;
j++;
}
l++;
j=0;
}
int max=res_vec[0];
for(int i =1;i<res_vec.size();i++)
{
if(max < res_vec[i])
{
max = res_vec[i];
}
//cout<<res_vec[i]<< " ";
}
res = max;
//cout<<endl;
return res;
}
// Complete the hourglassSum function below.
static int hourglassSum(int[][] arr) {
int max = Integer.MIN_VALUE;
for (int i = 0; i < arr.length - 2; i++) {
for (int j = 0; j < arr.length - 2; j++) {
int hourGlassSum = (arr[i][j] + arr[i][j + 1] + arr[i][j + 2])
+ (arr[i + 1][j + 1])
+ (arr[i + 2][j] + arr[i + 2][j + 1] + arr[i + 2][j + 2]);
max = Math.max(hourGlassSum,max);
}
}
return max;
}
public static int hourglassSum(List<List<Integer>> arr) {
// Write your code here
int maxSum = Integer.MIN_VALUE;
for (int i = 0; i < 4; i++) {
for (int j = 0; j < 4; j++) {
int sum = arr.get(i).get(j) +arr.get(i).get(j+1) +
arr.get(i).get(j+2)+arr.get(i+1).get(j+1)+
arr.get(i+2).get(j)+arr.get(i+2).get(j+1)+arr.get(i+2).get(j+2);
if (maxSum < sum) {
maxSum = sum;
}
}
}
return maxSum;
}
}
Iterative way,Passing all test cases in hackerank web
public static int hourglassSum(List<List<Integer>> arr) {
// Write your code here
int rowsCount=arr.size();
int colCount=arr.get(0).size();
Integer max=Integer.MIN_VALUE;
Integer subSum=0;
for(int r=0; (r+3)<=rowsCount; r++)
{
for(int c=0; (c+3)<=colCount; c++)
{
subSum= hourglassSubSum(arr,r,c);
System.out.println("r,c,subSum "+r+" "+c+" "+" "+subSum);
if(subSum>max)
{
max=subSum;
}
}
}
return max;
}
public static int hourglassSubSum(List<List<Integer>> hourglassArray,
int rowIndex,int colIndex) {
// Write your code here
Integer subSum=0;
for(int i=rowIndex;i<(rowIndex+3);i++)
{
for(int j=colIndex;j<(colIndex+3);j++)
{
if(i==(rowIndex+1) && (j==colIndex || j==colIndex+2))
{
continue;
}
subSum=subSum+hourglassArray.get(i).get(j);
}
}
return subSum;
}
Solution for actual "2D Array - DS" challenge from HackerRank https://www.hackerrank.com/challenges/2d-array
public static int hourglassSum(List<List<Integer>> arr) {
int maxSum = Integer.MIN_VALUE;
for (int col=0; col <= 3; col++) {
for (int row=0; row <= 3; row++) {
int sum = calcHourglass(arr, col, row);
maxSum = Math.max(sum, maxSum);
}
}
return maxSum;
}
private static int calcHourglass(List<List<Integer>> arr, int col, int row) {
int sum = 0;
for (int i=0; i < 3; i++) {
sum += arr.get(row).get(col+i); // the top of the hourglass
sum += arr.get(row+2).get(col+i); // the bottom of the hourglass
}
sum += arr.get(row+1).get(col+1); // the center
return sum;
}
import java.io.*;
import java.util.Scanner;
public class Solution {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int low = -9,high = 5;
int lh = low * high;
int sum = 0, i, j;
int max = 0;
int a[][] = new int[6][6];
for (i = 0; i < 6; i++) {
for (j = 0; j < 6; j++) {
a[i][j] = in.nextInt();
}
}
for (i = 0; i < 4; i++) {
for (j = 0; j < 4; j++) {
sum = (a[i][j] + a[i][j+1] + a[i][j+2]);
sum = sum + a[i+1][j+1];
sum = sum + (a[i+2][j] + a[i+2][j+1] + a[i+2][j+2]);
if (sum > lh) lh = sum;
}
}
System.out.print(lh);
}
}
Here you go..
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int a[][] = new int[6][6];
int max = 0;
for (int i = 0; i < 6; i++) {
for (int j = 0; j < 6; j++) {
a[i][j] = in.nextInt();
}
}
for (int i = 0; i < 4; i++) {
for (int j = 0; j < 4; j++) {
int sum = a[i][j] + a[i][j + 1] + a[i][j + 2] + a[i + 1][j + 1]
+ a[i + 2][j] + a[i + 2][j + 1] + a[i + 2][j + 2];
if (sum > max || (i == 0 && j == 0)) {
max = sum;
}
}
}
System.out.println(max);
}
I want to generate a matrix with consecutive numbers starting from 1, in this form
zig zag matrix
public static int[][] Zig_Zag(final int size) {
int[][] data = new int[size][size];
int i = 1;
int j = 1;
for (int element = 0; element < size * size; element++) {
data[i - 1][j - 1] = element;
if ((i + j) % 2 == 0) { // Even stripes if (j < size) j++; else i+=
// 2; if (i > 1) i--; } else { // Odd
// stripes if (i < size) i++; else j+= 2; if
// (j > 1) j--; } } return data; }
}
}
return data;
}
Can anybody help?
Try this
public static int[][] Zig_Zag(int size) {
int[][] a = new int[size][size];
int n = 1;
for (int r = size, c = 0; r >= 0; --r)
for (int i = r, j = c; i < size; ++i, ++j)
a[i][j] = n++;
for (int r = 0, c = 1; c < size; ++c)
for (int i = r, j = c; j < size; ++i, ++j)
a[i][j] = n++;
return a;
}
and
int[][] a = Zig_Zag(4);
for (int[] r : a)
System.out.println(Arrays.toString(r));
result:
[7, 11, 14, 16]
[4, 8, 12, 15]
[2, 5, 9, 13]
[1, 3, 6, 10]
Try this code :
public static int[][] Zig_Zag(final int size) {
int[][] data = new int[size][size];
int i = 1;
int j = 1;
for (int element = 1; element <= size * size; element++) {
data[i - 1][j - 1] = element;
if ((i + j) % 2 == 0) {
// Even stripes
if (j < size)
j++;
else
i += 2;
if (i > 1)
i--;
} else {
// Odd stripes
if (i < size)
i++;
else
j += 2;
if (j > 1)
j--;
}
}
return data;
}
public static void main(String[] args) {
int[][] data = Zig_Zag(4);
for(int i=0; i<data.length;i++){
for(int j=0; j<data[i].length;j++){
System.out.print(data[i][j]+" ");
}
System.out.println("");
}
}
Output:
1 2 6 7
3 5 8 13
4 9 12 14
10 11 15 16
Not a very elegant solution:
private static int triangle_below(int n) {
return n * (n + 1) / 2;
}
private static int except_triangle_above(int size, int n) {
return size * size - triangle_below(2 * size - n);
}
private static int[][] gen(int size) {
int[][] m = new int[size][size];
for (int i = 0; i < size; ++i) {
for (int j = 0; j < size; ++j) {
// already filled cells in lower diagonal layers
int k = Math.min(
triangle_below(i + j),
except_triangle_above(size, Math.max(size, i + j + 1))
);
// position in current layer
int l = Math.min(j + 1, size - i);
m[size - i - 1][j] = k + l;
}
}
return m;
}
Can anyone give me example about shell sort? I'm a new person in here who must learn about shell sort, but first I must find a Java shell sort example. I found one example in Google but it's too difficult.
Here, this code is very simple :
/**
* Shellsort, using Shell’s (poor) increments.
* #param a an array of Comparable items.
*/
public static <T extends Comparable<? super T>>
void shellsort( T [ ] a )
{
int j;
for( int gap = a.length / 2; gap > 0; gap /= 2 )
{
for( int i = gap; i < a.length; i++ )
{
T tmp = a[ i ];
for( j = i; j >= gap && tmp.compareTo( a[ j - gap ] ) < 0; j -= gap )
{
a[ j ] = a[ j - gap ];
}
a[ j ] = tmp;
}
}
}
I stole it from a book called Data Structures and Algorithm Analysis in Java. It is very good book easy to understand. I advise you to read it.
May be, this java code will help you.
public class ShellSort {
private long[] data;
private int len;
public ShellSort(int max) {
data = new long[max];
len = 0;
}
public void insert(long value){
data[len] = value;
len++;
}
public void display() {
System.out.print("Data:");
for (int j = 0; j < len; j++)
System.out.print(data[j] + " ");
System.out.println("");
}
public void shellSort() {
int inner, outer;
long temp;
//find initial value of h
int h = 1;
while (h <= len / 3)
h = h * 3 + 1; // (1, 4, 13, 40, 121, ...)
while (h > 0) // decreasing h, until h=1
{
// h-sort the file
for (outer = h; outer < len; outer++) {
temp = data[outer];
inner = outer;
// one subpass (eg 0, 4, 8)
while (inner > h - 1 && data[inner - h] >= temp) {
data[inner] = data[inner - h];
inner -= h;
}
data[inner] = temp;
}
h = (h - 1) / 3; // decrease h
}
}
public static void main(String[] args) {
int maxSize = 10;
ShellSort arr = new ShellSort(maxSize);
for (int j = 0; j < maxSize; j++) {
long n = (int) (java.lang.Math.random() * 99);
arr.insert(n);
}
arr.display();
arr.shellSort();
arr.display();
}
}
Shell sort improves insertion sort by comparing elements separated by a gap of several positions.
This lets an element take "bigger steps" toward its expected position. Multiple passes over the data are taken with smaller and smaller gap sizes. The last step of Shell sort is a plain insertion sort, but by then, the array of data is guaranteed to be almost sorted.
This code might help you in understanding the logic better.
package Sorts;
public class ShellSort extends Sorter{
#Override
public <T extends Comparable<? super T>> void sort(T[] a) {
int h = 1;
while((h*3+1) < a.length)
h = 3*h+1;
while(h > 0){
for(int i = h-1; i < a.length; i++){
T s = a[i];
int j = i;
for(j = i; (j>=h) && (a[j-h].compareTo(s) > 0); j-=h)
a[j] = a[j-h];
a[j] = s;
}
h /= 3;
}
}
}
Here is a visualization of shell sort for a python implementation:
def exch(a,i,j):
t = a[i]
a[i] = a[j]
a[j] = t
def shellsort(string):
print string
a = list(string)
N = len(a)
h = 1
i = 0
j = 0
k = 0
#determine starting stride length
while ( h < N/3 ):
h = 3*h + 1
print "STRIDE LENGTH: " + str(h)
while (h >=1):
i = h
while i < N:
j = i
k = j - h
while j >= h and a[j] < a[j-h]:
k = j - h
exch(a,j,k)
j -= h
i += 1
h = h/3
print "STRIDE LENGTH: " + str(h)
print ''.join(a)·
if __name__ == '__main__':
shellsort("astringtosortwithshellsort")
Here's an example:
public static void shellsort( Comparable [ ] a )
{
for( int gap = a.length / 2; gap > 0;
gap = gap == 2 ? 1 : (int) ( gap / 2.2 ) )
for( int i = gap; i < a.length; i++ )
{
Comparable tmp = a[ i ];
int j = i;
for( ; j >= gap && tmp.compareTo( a[ j - gap ] ) < 0; j -= gap )
a[ j ] = a[ j - gap ];
a[ j ] = tmp;
}
}
I find the easiest way to understand shell sort is to break it down into segments:
private static void shellsort() {
int[] theArray = {44,5,33,22,765,43,53,12,57,97};
//first section gets the Knuth's interval sequence (very efficient)
int h=1;
while(h<= theArray.length/3){
h = 3*h + 1; //h is equal to highest sequence of h<=length/3 (1,4,13,40...)
}
//next section
while(h>0){ //for array of length 10, h=4
//similar to insertion sort below
for(int i=0; i<theArray.length; i++){
int temp = theArray[i];
int j;
for(j=i; j>h-1 && theArray[j-h] >= temp; j=j-h){
a[j] = a[j-h];
}
a[j] = temp;
}
h = (h-1)/3;
}
}
Output: 5, 12, 22, 33, 43, 44, 53, 57, 97, 765
Classic primitive type implementation:
package math;
import java.util.Arrays;
public class Sorter{
public static void main(String []args){
int[] a = {9,8,7,6,5,4,3,2,1};//plz use sophisticated random number generator
System.out.println( Arrays.toString(a) );
System.out.println( Arrays.toString(shellSort(a)) );
}
//Performs a shell sort on an array of ints.
public static int[] shellSort(int[] array){
int h = 1;
while (h < array.length) h = 3*h + 1;
while (h > 0){
h = h/3;
for (int k = 0; k < h; k++){
for (int i = h+k; i < array.length; i+=h){
int key = array[i];
int j = i-h;
while (j>=0 && array[j] > key){
array[j+h] = array[j];
j-=h;
}
array[j+h] = key;
//-> invariant: array[0,h,2*h..j] is sorted
}
}
//->invariant: each h-sub-array is sorted
}
return array;
};
}
P.S.: Check this link for other sorting algorithms (they are in c++, though, easily portable to java).
package sort_tester;
public class ShellSorter extends Sorter {
private final int[] gapArray = {1750,701,301,132,57,23,10,4,1};
#Override
public void makeSort (boolean trace) {
int size = list.length;
int i,j, temp;
for ( int gap : gapArray ) {
i = gap;
while ( i < size ) {
temp = list[i];
j = i-gap;
while ( j >= 0 && list[j] > temp ) {
list[j + gap] = list[j];
j -= gap;
}
list[j + gap] = temp;
i ++;
}
}
}
}
list - is int[];
GapArray taken from arcticle of Marcin Ciura
http://sun.aei.polsl.pl/~mciura/publikacje/shellsort.pdf
Here is a video link: https://youtu.be/SCBf7aqKQEY
The guy has made a good video of shell sort!!
And a simple code:
int sort(int arr[])
{
int n = arr.length;
int gap = n/2;
int i,j;
while(gap>0)
{ for (i=0,j=i+gap; j<n; i++,++j)
{
if(arr[i]>arr[j]) //swap
{ int temp = arr[i];
arr[i]=arr[j];
arr[j]=temp;
}
}
gap=gap/2;
}
return 0;
}
Use this
public void shellSort(Integer[] arr) {
int interval = arr.length / 2;
while (interval != 0) {
for (int i = 0; i < interval; i++) {
for (int p = i + interval; p < arr.length; p += interval) {
int key = arr[p];
int j = p - interval;
while (j >= 0) {
if (key < arr[j]) {
arr[j + interval] = arr[j];
} else
break;
j -= interval;
}
arr[j + interval] = key;
}
}
interval /= 2;
}
}
Snippet with 3k+1 gap.
public void shellSort(Comparable arr[], int size, int h, int x) {
while (h >= 1) {
for (int i = 0; i <= size - h; i++) {
for (int j = i; j < size-h && (arr[j].compareTo(arr[j+h]) > 0); j += h)
swap(arr, j, j+h);
}
h = 3*(--x) + 1;
}
}