问:
Keyword 'with' not working in MySQL 8 Workbench
I have the following query:

```<code>with
    converted as (select convert(v using utf8mb4)
                         collate utf8mb4_0900_ai_ci as v from t),
    offending as (select v from converted group by v having count(*) > 1),
    duplicates as (select converted.v from converted join offending
                               where converted.v = offending.v)
select * from duplicates as a join duplicates as b
          where a.v = b.v and
          a.v collate utf8mb4_bin > b.v collate utf8mb4_bin;
</code>```

When I paste this in Workbench, it's saying the following:

"with is not valid at this position for this server version"

I am using the latest versions of MySQL 8.0.19 and Workbench 8.0.19.

When I use this query, this work just fine:

```<code>with
    converted as (select convert(band_or_artist using utf8mb4)
                         collate utf8mb4_0900_ai_ci as v from music_band_or_artist),
    offending as (select v from converted group by v having count(*) > 1)
select count(*) from offending;
</code>```

Can anyone help me rewrite this first query to work properly?

答:
The problem here is that once you consume your converted CTE in the offending definition, you can't use it again.  One workaround would be to define converting twice:

```<code>WITH converted1 AS (
    SELECT CONVERT(v using utf8mb4) COLLATE utf8mb4_0900_ai_ci AS v FROM t
),
converted2 AS (
    SELECT CONVERT(v using utf8mb4) COLLATE utf8mb4_0900_ai_ci AS v FROM t
),
offending AS (
    SELECT v FROM converted1 GROUP BY v HAVING COUNT(*) > 1
),
duplicates AS (
    SELECT c.v FROM converted2 c
    INNER JOIN offending o ON c.v = o.v
)
SELECT *
FROM duplicates a
INNER JOIN duplicates b
    ON a.v = b.v AND
       a.v COLLATE utf8mb4_bin > b.v COLLATE utf8mb4_bin;
</code>```

Body:
I have the following query:

with
    converted as (select convert(v using utf8mb4)
                         collate utf8mb4_0900_ai_ci as v from t),
    offending as (select v from converted group by v having count(*) > 1),
    duplicates as (select converted.v from converted join offending
                               where converted.v = offending.v)
select * from duplicates as a join duplicates as b
          where a.v = b.v and
          a.v collate utf8mb4_bin > b.v collate utf8mb4_bin;

When I paste this in Workbench, it's saying the following:

"with is not valid at this position for this server version"

I am using the latest versions of MySQL 8.0.19 and Workbench 8.0.19.

When I use this query, this work just fine:

with
    converted as (select convert(band_or_artist using utf8mb4)
                         collate utf8mb4_0900_ai_ci as v from music_band_or_artist),
    offending as (select v from converted group by v having count(*) > 1)
select count(*) from offending;

Can anyone help me rewrite this first query to work properly?

Body:
The problem here is that once you consume your converted CTE in the offending definition, you can't use it again.  One workaround would be to define converting twice:

WITH converted1 AS (
    SELECT CONVERT(v using utf8mb4) COLLATE utf8mb4_0900_ai_ci AS v FROM t
),
converted2 AS (
    SELECT CONVERT(v using utf8mb4) COLLATE utf8mb4_0900_ai_ci AS v FROM t
),
offending AS (
    SELECT v FROM converted1 GROUP BY v HAVING COUNT(*) > 1
),
duplicates AS (
    SELECT c.v FROM converted2 c
    INNER JOIN offending o ON c.v = o.v
)
SELECT *
FROM duplicates a
INNER JOIN duplicates b
    ON a.v = b.v AND
       a.v COLLATE utf8mb4_bin > b.v COLLATE utf8mb4_bin;


来源: stackexchange

问:
Html Helper for IEnumerable<T> collection

I have two classes MyClassA and MyClassB:

```<code>public class MyClassA
{
    public int Age { get; set; }
    public string Name { get; set; }
}

public class MyClassB
{
    public IEnumerable<MyClassA> Data { get; set; }
}
</code>```

Now, I want to create custom strongly typed html helper to generate textboxes with names from  collection MyClassA, something like this:

```<code>@model MyClassB

@Html.MyTextBoxFor(p => p.MapFrom(o => o.Age))
@Html.MyTextBoxFor(p => p.MapFrom(o => o.Name))
</code>```

... with the output:

```<code><input type="text" name="Age" />
<input type="text" name="Name" />
</code>```

How can I accomplish this?

PS. I know, I can write sth like this:

```<code>@Html.TextBoxFor(p => p.Data.First().Name)
</code>```

but it feels so wrong and inelegant...

Any ideas?

答:
Let me make sure I understand this correctly... you want to create a textbox for Name and Age for each MyClassA in Data property of MyClassB. If so, then editor templates to the rescue.

Create /Views/Shared/EditorTemplates/MyClassA.cshtml

```<code>@model MyClassA

@Html.TextBoxFor(m => m.Name)
@Html.TextBoxFor(m => m.Age)
</code>```

then in you view:

```<code>@model MyClassB

@Html.EditorFor(m => m.Data)
</code>```

ContentLicense: CC BY-SA 3.0

Body:
I have two classes MyClassA and MyClassB:

public class MyClassA
{
    public int Age { get; set; }
    public string Name { get; set; }
}

public class MyClassB
{
    public IEnumerable<MyClassA> Data { get; set; }
}

Now, I want to create custom strongly typed html helper to generate textboxes with names from  collection MyClassA, something like this:

@model MyClassB

@Html.MyTextBoxFor(p => p.MapFrom(o => o.Age))
@Html.MyTextBoxFor(p => p.MapFrom(o => o.Name))

... with the output:

<input type="text" name="Age" />
<input type="text" name="Name" />

How can I accomplish this?

PS. I know, I can write sth like this:

@Html.TextBoxFor(p => p.Data.First().Name)

but it feels so wrong and inelegant...

Any ideas?

Body:
Let me make sure I understand this correctly... you want to create a textbox for Name and Age for each MyClassA in Data property of MyClassB. If so, then editor templates to the rescue.

Create /Views/Shared/EditorTemplates/MyClassA.cshtml

@model MyClassA

@Html.TextBoxFor(m => m.Name)
@Html.TextBoxFor(m => m.Age)

then in you view:

@model MyClassB

@Html.EditorFor(m => m.Data)


问:
Using multer with nodejs
I am trying to upload a file from my page to node server.

I can see form data are arriving in the router on server.

But no file is saved in upload folder.

What am I doing wrong?

//router unit

```<code>const express = require('express');
const router = express.Router();
const multer = require('multer');
const storage = multer.diskStorage({
    destination: (req, file, cb) => {
        console.log('chegei')
        cb(null, "uploads/")
    },
    filename: (req, file, cb) => {
        console.log('chegei2')
        cb(null, Date.now() + "-" + file.ogirinalname)
    },
});

module.exports = function (page) {
     router.post('/SendMsgBase64', async (req, res) => {
        var upload = multer({ storage: storage }).single('userFile');
        upload(req, res, function (err) {
            if (err) {
                console.log(err);
                return res.send({ "data": "Error uploading file." });
            }
            return res.send({ "data": "File is uploaded" });
        });
  return router
}
</code>```

//app.js unit

```<code>const express = require('express')
const app = express()
const server = require('http').Server(app)
const io = require('socket.io')(server)
const WARoutes = require('../routes/WARoutes');
const path = require('path');
const bodyParser = require('body-parser');

app.use(bodyParser.json()); // support json encoded bodies
app.use(bodyParser.urlencoded({ extended: true })); // support encoded bodies
app.use(express.urlencoded({ extended: true }))
app.get('/', (req, res) => {
    res.sendFile('/index.html');
})
app.use('/whats', WARoutes(this.page));
</code>```

//html

```<code>  <form id="uploadForm">
      <input type="file" name="userFile" />
      <input type="button" value="Upload Image" onclick="uploadFile();">
      <span id="status"></span>
    </form>

    <script>
      uploadFile = () => {
        var formData = new FormData();
        debugger
        var logoImg = $('input[name="userFile"]').get(0).files[0];

        formData.append('logo', logoImg);
        var objArr = [];

        objArr.push({ "id": "123", "name": "luiz" });

        //JSON obj
        formData.append('objArr', JSON.stringify(objArr));

        $.ajax({
          url: "/whats/SendMsgBase64",
          type: "POST",
          processData: false,
          contentType: "application/x-www-form-urlencoded",
          data: formData,
          complete: function (data) {
            alert("success");
          }
        })
      };
    </script>
</code>```

答:
According to multer's github page, if you have not created the uploads directory, it may go something wrong.

If this is the case, creating the directory on your own or passing a string value to destination property is the solution for you.

https://github.com/expressjs/multer

Note: You are responsible for creating the directory when providing destination as a function. When passing a string, multer will make sure that the directory is created for you.

ContentLicense: CC BY-SA 4.0

Title: Using multer with nodejs

Body:
I am trying to upload a file from my page to node server.

I can see form data are arriving in the router on server.

But no file is saved in upload folder.

What am I doing wrong?

//router unit

const express = require('express');
const router = express.Router();
const multer = require('multer');
const storage = multer.diskStorage({
    destination: (req, file, cb) => {
        console.log('chegei')
        cb(null, "uploads/")
    },
    filename: (req, file, cb) => {
        console.log('chegei2')
        cb(null, Date.now() + "-" + file.ogirinalname)
    },
});

module.exports = function (page) {
     router.post('/SendMsgBase64', async (req, res) => {
        var upload = multer({ storage: storage }).single('userFile');
        upload(req, res, function (err) {
            if (err) {
                console.log(err);
                return res.send({ "data": "Error uploading file." });
            }
            return res.send({ "data": "File is uploaded" });
        });
  return router
}

//app.js unit

const express = require('express')
const app = express()
const server = require('http').Server(app)
const io = require('socket.io')(server)
const WARoutes = require('../routes/WARoutes');
const path = require('path');
const bodyParser = require('body-parser');

app.use(bodyParser.json()); // support json encoded bodies
app.use(bodyParser.urlencoded({ extended: true })); // support encoded bodies
app.use(express.urlencoded({ extended: true }))
app.get('/', (req, res) => {
    res.sendFile('/index.html');
})
app.use('/whats', WARoutes(this.page));

//html

  <form id="uploadForm">
      <input type="file" name="userFile" />
      <input type="button" value="Upload Image" onclick="uploadFile();">

    </form>


问:
How to automate recoding of many variables using mutate_at and nested ifelse statement?
There is a large data set consisting of repeated measures of the same variable on each subject. An example data is as below

```<code>df<-data.frame(
"id"=c(1:5),
"ax1"=c(1,6,8,15,17),
"bx1"=c(2,16,8,15,17))
</code>```

where "x1" is measured repeatedly so we can have "ax1", "bx1", "cx1" and so on. I am trying to recode these variables. The plan is to recode 1 and any number on the range from 3 to 12 (inclusively) as 0 and recode 2 or any value greater than or equal to 13 as 1. Because it involves many variables I am making use of "mutate_at" to automate the recoding. Also, the numbers to take on the same code are not consecutive (e.g. 1 and 3-12 to be recoded as 0) so I used a nested "ifelse" statement. I tried the following

```<code>df1<-df %>%
mutate_at(vars(ends_with("x1")),factor,
        ifelse(x1>=3 & x1 <=12,0,ifelse(x1==1, 0,
               ifelse(x1==2, 1,0))))
</code>```

However, this fails to work because R cannot recognize "x1". Any help on this is greatly appreciated in advance. The expected output would look like

```<code>> df1
   id ax1 bx1
1  1   0   1
2  2   0   1
3  3   0   0
4  4   1   1
5  5   1   1
</code>```

Body:
There is a large data set consisting of repeated measures of the same variable on each subject. An example data is as below

df<-data.frame(
"id"=c(1:5),
"ax1"=c(1,6,8,15,17),
"bx1"=c(2,16,8,15,17))

where "x1" is measured repeatedly so we can have "ax1", "bx1", "cx1" and so on. I am trying to recode these variables. The plan is to recode 1 and any number on the range from 3 to 12 (inclusively) as 0 and recode 2 or any value greater than or equal to 13 as 1. Because it involves many variables I am making use of "mutate_at" to automate the recoding. Also, the numbers to take on the same code are not consecutive (e.g. 1 and 3-12 to be recoded as 0) so I used a nested "ifelse" statement. I tried the following

df1<-df %>%
mutate_at(vars(ends_with("x1")),factor,
        ifelse(x1>=3 & x1 <=12,0,ifelse(x1==1, 0,
               ifelse(x1==2, 1,0))))

However, this fails to work because R cannot recognize "x1". Any help on this is greatly appreciated in advance. The expected output would look like

> df1
   id ax1 bx1
1  1   0   1
2  2   0   1
3  3   0   0
4  4   1   1
5  5   1   1

Body:
Using ifelse, we can proceed as follows:

df %>%
   mutate_at(vars(ends_with("x1")),~ifelse(. ==1 | . %in% 3:12,0,
                                           ifelse(. ==2 | .>=13,1,.)))
  id ax1 bx1
1  1   0   1
2  2   0   1
3  3   0   0
4  4   1   1
5  5   1   1


Title: How to automate recoding of many variables using mutate_at and nested ifelse statement?

Body:
We can use case_when

library(dplyr)

df %>%
  mutate_at(vars(ends_with("x1")), ~case_when((. >= 3 & . <= 12) | . == 1 ~ 0,
                                               . >= 13 | . == 2 ~ 1))

#  id ax1 bx1
#1  1   0   1
#2  2   0   1
#3  3   0   0
#4  4   1   1
#5  5   1   1


问:
Correct approach to avoid rendering view in Action
I currently use an ajax post back to an action to create a new database object and then return the rendered html for a view of that object. I then inject that html into the page.

I was wondering, since MVC does easily allow you to render views to HTML from within controllers, if there was a better (or more correct) approach to the problem.

(I currently use this code to render the view as html in the action).

Any and all ideas appreciated.

答: You can render a PartialView as the other answer suggested or return JsonResult and populate your HTML from the JSON data.  Your call.</p>


问:
Where option -> New > Vector Asset on Android Studio?
I would like to add an SVG image to the Res folder. Right-click to option in the res -> add new file... there is no Asset Vector... Why? What is wrong?

答: Try using different version of Android (before 4.4) for "Vector Assert" to appear in a "New" context menu. Path to Vector Asset</p>


问:
Reading large table by chunks
I have a table generated on a server and I connect to it using a presto client as follows:

```<code>conn = presto.connect('hostname',port)
db = "some_large_table"
</code>```

What I would like to do is  to read in 1 chunk at a time then do my processing and append that chunk to an existing df. Ie:

```<code>sql = "select column1, .. column20 limit 100"
chunk_count = 0
dfs = []

for chunk in pd.read_sql_query(sql, conn, chunksize=10) :
    chunk_count +=1
    dfs.append(chunk)

print(dfs[['column1', 'column2']])
</code>```

The print dfs only shows 10 rows. Which Means its not appending.

答:
Well I can't be sure that this will work without more context but I can tell you that your issue arises because dfs is a list of data frames not a data frame... That said with this approach you will assign dfs to be equal to your first query and append subsequent querys to that result.</p>

```<code>sql = "select column1, .. column20 limit 100"
chunk_count = 0

for chunk in pd.read_sql_query(sql, conn, chunksize=10) :
    chunk_count +=1
    try:
        dfs.append(chunk)
    except:
        dfs = chunk

print(dfs[['column1', 'column2']])
</code>```

Title: Reading large table by chunks

Body:
I have a table generated on a server and I connect to it using a presto client as follows:

conn = presto.connect('hostname',port)
db = "some_large_table"

What I would like to do is  to read in 1 chunk at a time then do my processing and append that chunk to an existing df. Ie:

sql = "select column1, .. column20 limit 100"
chunk_count = 0
dfs = []

for chunk in pd.read_sql_query(sql, conn, chunksize=10) :
    chunk_count +=1
    dfs.append(chunk)

print(dfs[['column1', 'column2']])

The print dfs only shows 10 rows. Which Means its not appending.

Body:
Well I can't be sure that this will work without more context but I can tell you that your issue arises because dfs is a list of data frames not a data frame... That said with this approach you will assign dfs to be equal to your first query and append subsequent querys to that result.

sql = "select column1, .. column20 limit 100"
chunk_count = 0

for chunk in pd.read_sql_query(sql, conn, chunksize=10) :
    chunk_count +=1
    try:
        dfs.append(chunk)
    except:
        dfs = chunk

print(dfs[['column1', 'column2']])


问:
Redirect with .htaccess URLs matching a prefix to a subfolder
In a multilingual website I am trying to set a rule in .htaccess, so that the URLs that are contained in a folder, and that are matching a prefix, are redirected into a sub-folder.

In concrete:

www.example.com/es/urlprefix* ==> www.example.com/es/subfolder/urlprefix*

Example:

```<code>www.example.com/es/urlprefix_example
</code>```

is redirected to

```<code>www.example.com/es/subfolder/urlprefix_example
</code>```

I would also like to know how to do the reverse, that is:

www.example.com/es/subfolder/urlprefix* ==> www.example.com/es/urlprefix*

答:
Try the following at the top of your .htaccess file to redirect to the subfolder:

```<code>RewriteEngine On

RewriteRule ^(es)/(urlprefix.*) /$1/subfolder/$2 [R,L]
</code>```

To redirect the other way (to remove the subfolder) you could do something like this:

```<code>RewriteRule ^(es)/subfolder/(urlprefix.*) /$1/$2 [R,L]
</code>```

Obviously you can't do both at the same time, without some additional conditions, otherwise you'll get a redirect loop.

Body:
In a multilingual website I am trying to set a rule in .htaccess, so that the URLs that are contained in a folder, and that are matching a prefix, are redirected into a sub-folder.

In concrete:

www.example.com/es/urlprefix* ==> www.example.com/es/subfolder/urlprefix*

Example:

www.example.com/es/urlprefix_example

is redirected to

www.example.com/es/subfolder/urlprefix_example

I would also like to know how to do the reverse, that is:

www.example.com/es/subfolder/urlprefix* ==> www.example.com/es/urlprefix*

Body:
Try the following at the top of your .htaccess file to redirect to the subfolder:

RewriteEngine On

RewriteRule ^(es)/(urlprefix.*) /$1/subfolder/$2 [R,L]

To redirect the other way (to remove the subfolder) you could do something like this:

RewriteRule ^(es)/subfolder/(urlprefix.*) /$1/$2 [R,L]

Obviously you can't do both at the same time, without some additional conditions, otherwise you'll get a redirect loop.


问:
Rails: order the results returned from DISTINCT ON * ORDER
I have the following Rails models: Chat and Messages where a chat can have many messages. I have the following Rails query to pull the last message from the user for each chat where he is a recipient:

```<code>def index
  messages = Message.where(recipient_id: id)
                    .select('DISTINCT ON ("chat_id") *')
                    .order(:chat_id, created_at)
end
</code>```

This gives me the last message to the user of each chat that the user is a part of. I would now like to sort the results of this query by when the messages were created so that the latest messages go to the top. However, if I add

sorted = messages.order(created_at: :desc)

It doesn't sort the results of the first query, it simply appends the order by to the first query (which I know is the expected behavior) so I don't get a sorted list by created date. How can I do an order by to the result of the first query? Essentially something that would mimic the following with Rails syntax:

```<code>SELECT *
FROM (SELECT DISTINCT ON (chat_id) *
      FROM messages
      ORDER BY chat_id, created_at DESC) last_messages
ORDER BY created_at DESC
</code>```

答:
The first option is to unscope the :order of messages then order it again with your desired column.

```<code>sorted = messages.unscope(:order).order(created_at: :desc)
</code>```

In case you can't unscope the messages, another option is turning messages into a subquery.

```<code>sorted = Message.where(id: messages).order(created_at: :desc)
</code>```

Body:
I have the following Rails models: Chat and Messages where a chat can have many messages. I have the following Rails query to pull the last message from the user for each chat where he is a recipient:

def index
  messages = Message.where(recipient_id: id)
                    .select('DISTINCT ON ("chat_id") *')
                    .order(:chat_id, created_at)
end

This gives me the last message to the user of each chat that the user is a part of. I would now like to sort the results of this query by when the messages were created so that the latest messages go to the top. However, if I add

sorted = messages.order(created_at: :desc)

It doesn't sort the results of the first query, it simply appends the order by to the first query (which I know is the expected behavior) so I don't get a sorted list by created date. How can I do an order by to the result of the first query? Essentially something that would mimic the following with Rails syntax:

SELECT *
FROM (SELECT DISTINCT ON (chat_id) *
      FROM messages
      ORDER BY chat_id, created_at DESC) last_messages
ORDER BY created_at DESC

Body:
The first option is to unscope the :order of messages then order it again with your desired column.

sorted = messages.unscope(:order).order(created_at: :desc)

In case you can't unscope the messages, another option is turning messages into a subquery.

sorted = Message.where(id: messages).order(created_at: :desc)


问:
How to join elements in array based on their value
This is my array

```<code>["9", "8", "4", "×", "5", "4", "3"]
</code>```

I want to join the elements before and after "×" so that I have

```<code>stringA = "984"
</code>```

and

```<code>stringB = "543"
</code>```

How do I do that?

答:
I'd join by the empty string, then split by × and destructure:

const arr = ["9", "8", "4", "×", "5", "4", "3"];
const [stringA, stringB] = arr.join('').split('×');
console.log(stringA, stringB);```

Body:
This is my array

["9", "8", "4", "×", "5", "4", "3"]

I want to join the elements before and after "×" so that I have

stringA = "984"

and

stringB = "543"

How do I do that?


问:
Attempting to tamper proof my executable with some hashing but coming across some unexpected and unknown compiler behaviour
In an attempt to tamper proof my executable with some hashing I've come across some unexpected and unknown compiler behaviour.

I have this idea of calculating a simple hash value of my program by simply adding all the bytes in the binary and using the remainder of that total divided by 256 as a hash value.

I figured that if in my program I have a string literal of "0000" and that the hash I calculate with the above algorithm gives for example, 163, that I could get 164 by replacing one of the '0' with a '1'. However the results I get are far from that. By replacing a single character by a single value I get a totally different hash result. For this example the 163 could become 84, which puzzles me.

My function for calculating the hash is quite simple but here it is anyway.

```<code>int calcHash(const char *filename) {
    int hash = 0;
    int c;
    FILE *fh = fopen(filename, "r");

    if (!fh)
        return -1;

    while((c = fgetc(fh)) != EOF)
        hash = (hash + c) % 256;

    fclose(fh);

    return hash;
}
</code>```

And I call it from main() with this statement.

```<code>int hash = calcHash(argv[0]);
</code>```

What exactly happens during compilation? Anyway I can get more predictable hash values?

Perhaps this doesn't happen with all compilers. I am just totally baffled with that unexpected behaviour.

I'm using gcc on Ubuntu.

答:
This is a harder problem than it looks, as well as being a worse idea than it looks - I can't un-recommend this enough.

I worked on a customer system where they did this, and it was as much of a pain in the ass as has been suggested, so I ended up reverse engineering it to write my own re-seal utility so I could edit the damn file and apply the new hash. And these changes were always to the benefit of the software vendor and its customers, never to steal it or anything.

But in any case, as best as I can remember it worked by including some data areas in the code:

```<code>char tamper_marker_1[] = "SOME MAGIC STRING";
int  fileSize;
unsigned checksum;
char endmarker[] = "OTHER MAGIC STRING";
</code>```

The external apply-seal program would open the .exe and find the magic  string, which lead to the above data area, and would stuff in the fileSize and the checksum of all data other than in the seal-info area.

The executable would test for tampering by opening itself as a file, and performing the same checks.

Under Windows, you can use GetModuleFilename() to find the full path of the executable, and on Linux you can open /proc/12345/exe (where 12345 is your process ID) which is a symbolic link to the program and so the same thing.

I don't know if I'm contributing to making the world a worse place by describing this, but SO is for questions and answers, and perhaps there's a legitimate need. Please don't do it unless you really, really have to.

EDIT: You might point out that very few will go to the trouble I did of reverse engineering, but I'll point out that all you need is one person to create the re-seal tool and release it, and all your clever work is for naught.

EDIT2: As I think about this, if it's just one program, you wouldn't have to actually reverse engineer the algorithm - you'd just have to be able to disassemble it to nop-out the test.

Body:
In an attempt to tamper proof my executable with some hashing I've come across some unexpected and unknown compiler behaviour.

I have this idea of calculating a simple hash value of my program by simply adding all the bytes in the binary and using the remainder of that total divided by 256 as a hash value.

I figured that if in my program I have a string literal of "0000" and that the hash I calculate with the above algorithm gives for example, 163, that I could get 164 by replacing one of the '0' with a '1'. However the results I get are far from that. By replacing a single character by a single value I get a totally different hash result. For this example the 163 could become 84, which puzzles me.

My function for calculating the hash is quite simple but here it is anyway.

int calcHash(const char *filename) {
    int hash = 0;
    int c;
    FILE *fh = fopen(filename, "r");

    if (!fh)
        return -1;

    while((c = fgetc(fh)) != EOF)
        hash = (hash + c) % 256;

    fclose(fh);

    return hash;
}

And I call it from main() with this statement.

int hash = calcHash(argv[0]);

What exactly happens during compilation? Anyway I can get more predictable hash values?

Perhaps this doesn't happen with all compilers. I am just totally baffled with that unexpected behaviour.

I'm using gcc on Ubuntu.

Body:
This is a harder problem than it looks, as well as being a worse idea than it looks - I can't un-recommend this enough.

I worked on a customer system where they did this, and it was as much of a pain in the ass as has been suggested, so I ended up reverse engineering it to write my own re-seal utility so I could edit the damn file and apply the new hash. And these changes were always to the benefit of the software vendor and its customers, never to steal it or anything.

But in any case, as best as I can remember it worked by including some data areas in the code:

char tamper_marker_1[] = "SOME MAGIC STRING";
int  fileSize;
unsigned checksum;
char endmarker[] = "OTHER MAGIC STRING";

The external apply-seal program would open the .exe and find the magic  string, which lead to the above data area, and would stuff in the fileSize and the checksum of all data other than in the seal-info area.

The executable would test for tampering by opening itself as a file, and performing the same checks.

Under Windows, you can use GetModuleFilename() to find the full path of the executable, and on Linux you can open /proc/12345/exe (where 12345 is your process ID) which is a symbolic link to the program and so the same thing.

I don't know if I'm contributing to making the world a worse place by describing this, but SO is for questions and answers, and perhaps there's a legitimate need. Please don't do it unless you really, really have to.

EDIT: You might point out that very few will go to the trouble I did of reverse engineering, but I'll point out that all you need is one person to create the re-seal tool and release it, and all your clever work is for naught.

EDIT2: As I think about this, if it's just one program, you wouldn't have to actually reverse engineer the algorithm - you'd just have to be able to disassemble it to nop-out the test.


问:
Consolidate different alternative names of countries, under the official name
I'm searching for a list or python packages, to help me unify under one name different names of countries.

For example:

```<code>USA, SUA, United States, Unites States of America
Germany, Federal Republic of Germany, Deutschland, Duitsland
</code>```

I want to consolidate them under the official name, and allocate them iso standard.

答:
There is a well-documented and a pretty powerful library to do this and similar things in the project:

https://pypi.org/project/pycountry/

It covers not only short / official / unofficial names for countries, but also works properly with different Unicode subtleties:

There’s also a “fuzzy” search to help people discover “proper” countries for names that might only actually be subdivisions. The fuzziness also includes normalizing unicode accents. There’s also a bit of prioritization included to prefer matches on country names before subdivision names and have countries with more matches be listed before ones with fewer matches:

```<code>pycountry.countries.search_fuzzy('England')
[Country(alpha_2='GB', alpha_3='GBR', name='United Kingdom', numeric='826', official_name='United Kingdom of Great Britain and Northern Ireland')]
</code>```

Body:
I'm searching for a list or python packages, to help me unify under one name different names of countries.

For example:

USA, SUA, United States, Unites States of America
Germany, Federal Republic of Germany, Deutschland, Duitsland

I want to consolidate them under the official name, and allocate them iso standard.

Body:
There is a well-documented and a pretty powerful library to do this and similar things in the project:

https://pypi.org/project/pycountry/

It covers not only short / official / unofficial names for countries, but also works properly with different Unicode subtleties:

There’s also a “fuzzy” search to help people discover “proper” countries for names that might only actually be subdivisions. The fuzziness also includes normalizing unicode accents. There’s also a bit of prioritization included to prefer matches on country names before subdivision names and have countries with more matches be listed before ones with fewer matches:

pycountry.countries.search_fuzzy('England')
[Country(alpha_2='GB', alpha_3='GBR', name='United Kingdom', numeric='826', official_name='United Kingdom of Great Britain and Northern Ireland')]


问:
InvalidValueError: setIcon: not a string; and not an instance of PinView; and no url property; and no path property
I am working on an app that uses the search box feature in the Google Maps/Places APIs to look up food banks near their local city or address.

The client-side looks fine in testing, but under the hood I keep getting the following error message in the console: "InvalidValueError: setIcon: not a string; and not an instance of PinView; and no url property; and no path property". It doesn't seem to be affecting the searches being entered/returned and returns everything that fits the search query. I'm not sure what needs to be done for the error to go away. Any suggestions? Thanks so much!

Here is my JS code:

```<code>function initAutocomplete() {

    let map = new google.maps.Map(document.getElementById('map'), {
        center: {lat: 32.714286, lng: -117.155577},
        scrollwheel: false,
        zoom: 12,
        maptypeId: 'roadmap'
    });

    let input = document.getElementById('pac-input');
    let searchBox = new google.maps.places.SearchBox(input);
    map.controls[google.maps.ControlPosition.TOP_LEFT].push(input);

    map.addListener('bounds_changed', function() {
      searchBox.setBounds(map.getBounds());
    });

    let markers = [];

    searchBox.addListener('places_changed', function() {
      let places = searchBox.getPlaces();

      if (places.length == 0) {
        return;
      }

      markers.forEach(function(marker) {
        marker.setMap(null);
      });
      markers = [];

      let bounds = new google.maps.LatLngBounds();
      places.forEach(function(place) {
        if (!place.geometry) {
          console.log("Returned place contains no geometry");
          return;
        }

        let icon = {
          url: places.icon,
          size: new google.maps.Size(71, 71),
          origin: new google.maps.Point(0, 0),
          anchor: new google.maps.Point(17, 34),
          scaledSize: new google.maps.Size(25, 25)
        };

        markers.push(new google.maps.Marker({
          map: map,
          icon: icon,
          title: place.name,
          position: place.geometry.location
        }));

        if (place.geometry.viewport) {
          bounds.union(place.geometry.viewport);
        } else {
          bounds.extend(place.geometry.location);
        }
      });

      map.fitBounds(bounds);
      });
}
</code>```

答:
This is invalid: url: places.icon,.  places is an Array and doesn't have a .icon property.  That means url is undefined, giving the error: InvalidValueError: setIcon: not a string; and not an instance of PinView; and no url property; and no path property.

Use url: place.icon, instead (the forEach assigns each element of the array to the place variable in its callback function).

Note (from comments): If you want the default red marker, don't use the icons from the place response (remove the line icon: icon, from the marker constructor, and the definition of the icon object)

```<code>places.forEach(function(place) {
  if (!place.geometry) {
    console.log("Returned place contains no geometry");
    return;
  }

  let icon = {
    url: place.icon,
    size: new google.maps.Size(71, 71),
    origin: new google.maps.Point(0, 0),
    anchor: new google.maps.Point(17, 34),
    scaledSize: new google.maps.Size(25, 25)
  };

  markers.push(new google.maps.Marker({
    map: map,
    icon: icon,
    title: place.name,
    position: place.geometry.location
  }));

  if (place.geometry.viewport) {
    bounds.union(place.geometry.viewport);
  } else {
    bounds.extend(place.geometry.location);
  }
});
</code>```

proof of concept fiddle

code snippet:

function initAutocomplete() {

  let map = new google.maps.Map(document.getElementById('map'), {
    center: {
      lat: 32.714286,
      lng: -117.155577
    },
    scrollwheel: false,
    zoom: 12,
    maptypeId: 'roadmap'
  });

  let input = document.getElementById('pac-input');
  let searchBox = new google.maps.places.SearchBox(input);
  map.controls[google.maps.ControlPosition.TOP_LEFT].push(input);

  map.addListener('bounds_changed', function() {
    searchBox.setBounds(map.getBounds());
  });

  let markers = [];

  searchBox.addListener('places_changed', function() {
    let places = searchBox.getPlaces();

    if (places.length == 0) {
      return;
    }

    markers.forEach(function(marker) {
      marker.setMap(null);
    });
    markers = [];

    let bounds = new google.maps.LatLngBounds();
    places.forEach(function(place) {
      if (!place.geometry) {
        console.log("Returned place contains no geometry");
        return;
      }

      let icon = {
        url: place.icon,
        size: new google.maps.Size(71, 71),
        origin: new google.maps.Point(0, 0),
        anchor: new google.maps.Point(17, 34),
        scaledSize: new google.maps.Size(25, 25)
      };

      markers.push(new google.maps.Marker({
        map: map,
        icon: icon,
        title: place.name,
        position: place.geometry.location
      }));

      if (place.geometry.viewport) {
        bounds.union(place.geometry.viewport);
      } else {
        bounds.extend(place.geometry.location);
      }
    });

    map.fitBounds(bounds);
  });
}```
<pre class="snippet-code-css lang-css prettyprint-override"><code>/* Always set the map height explicitly to define the size of the div
 * element that contains the map. */

#map {
  height: 90%;
}

/* Optional: Makes the sample page fill the window. */

html,
body {
  height: 100%;
  margin: 0;
  padding: 0;
}

#description {
  font-family: Roboto;
  font-size: 15px;
  font-weight: 300;
}

#infowindow-content .title {
  font-weight: bold;
}

#infowindow-content {
  display: none;
}

#map #infowindow-content {
  display: inline;
}

.pac-card {
  margin: 10px 10px 0 0;
  border-radius: 2px 0 0 2px;
  box-sizing: border-box;
  -moz-box-sizing: border-box;
  outline: none;
  box-shadow: 0 2px 6px rgba(0, 0, 0, 0.3);
  background-color: #fff;
  font-family: Roboto;
}

#pac-container {
  padding-bottom: 12px;
  margin-right: 12px;
}

.pac-controls {
  display: inline-block;
  padding: 5px 11px;
}

.pac-controls label {
  font-family: Roboto;
  font-size: 13px;
  font-weight: 300;
}

#pac-input {
  background-color: #fff;
  font-family: Roboto;
  font-size: 15px;
  font-weight: 300;
  margin-left: 12px;
  padding: 0 11px 0 13px;
  text-overflow: ellipsis;
  width: 400px;
}

#pac-input:focus {
  border-color: #4d90fe;
}

#title {
  color: #fff;
  background-color: #4d90fe;
  font-size: 25px;
  font-weight: 500;
  padding: 6px 12px;
}</code>```

  <input id="pac-input" type="text" placeholder="Enter a location" value="starbuck near New York city">

```

Body:
I am working on an app that uses the search box feature in the Google Maps/Places APIs to look up food banks near their local city or address.

The client-side looks fine in testing, but under the hood I keep getting the following error message in the console: "InvalidValueError: setIcon: not a string; and not an instance of PinView; and no url property; and no path property". It doesn't seem to be affecting the searches being entered/returned and returns everything that fits the search query. I'm not sure what needs to be done for the error to go away. Any suggestions? Thanks so much!

Here is my JS code:

function initAutocomplete() {

    let map = new google.maps.Map(document.getElementById('map'), {
        center: {lat: 32.714286, lng: -117.155577},
        scrollwheel: false,
        zoom: 12,
        maptypeId: 'roadmap'
    });

    let input = document.getElementById('pac-input');
    let searchBox = new google.maps.places.SearchBox(input);
    map.controls[google.maps.ControlPosition.TOP_LEFT].push(input);

    map.addListener('bounds_changed', function() {
      searchBox.setBounds(map.getBounds());
    });

    let markers = [];

    searchBox.addListener('places_changed', function() {
      let places = searchBox.getPlaces();

      if (places.length == 0) {
        return;
      }

      markers.forEach(function(marker) {
        marker.setMap(null);
      });
      markers = [];

      let bounds = new google.maps.LatLngBounds();
      places.forEach(function(place) {
        if (!place.geometry) {
          console.log("Returned place contains no geometry");
          return;
        }

        let icon = {
          url: places.icon,
          size: new google.maps.Size(71, 71),
          origin: new google.maps.Point(0, 0),
          anchor: new google.maps.Point(17, 34),
          scaledSize: new google.maps.Size(25, 25)
        };

        markers.push(new google.maps.Marker({
          map: map,
          icon: icon,
          title: place.name,
          position: place.geometry.location
        }));

        if (place.geometry.viewport) {
          bounds.union(place.geometry.viewport);
        } else {
          bounds.extend(place.geometry.location);
        }
      });

      map.fitBounds(bounds);
      });
}

Body:
This is invalid: url: places.icon,.  places is an Array and doesn't have a .icon property.  That means url is undefined, giving the error: InvalidValueError: setIcon: not a string; and not an instance of PinView; and no url property; and no path property.

Use url: place.icon, instead (the forEach assigns each element of the array to the place variable in its callback function).

Note (from comments): If you want the default red marker, don't use the icons from the place response (remove the line icon: icon, from the marker constructor, and the definition of the icon object)

places.forEach(function(place) {
  if (!place.geometry) {
    console.log("Returned place contains no geometry");
    return;
  }

  let icon = {
    url: place.icon,
    size: new google.maps.Size(71, 71),
    origin: new google.maps.Point(0, 0),
    anchor: new google.maps.Point(17, 34),
    scaledSize: new google.maps.Size(25, 25)
  };

  markers.push(new google.maps.Marker({
    map: map,
    icon: icon,
    title: place.name,
    position: place.geometry.location
  }));

  if (place.geometry.viewport) {
    bounds.union(place.geometry.viewport);
  } else {
    bounds.extend(place.geometry.location);
  }
});

proof of concept fiddle

code snippet:

function initAutocomplete() {

  let map = new google.maps.Map(document.getElementById('map'), {
    center: {
      lat: 32.714286,
      lng: -117.155577
    },
    scrollwheel: false,
    zoom: 12,
    maptypeId: 'roadmap'
  });

  let input = document.getElementById('pac-input');
  let searchBox = new google.maps.places.SearchBox(input);
  map.controls[google.maps.ControlPosition.TOP_LEFT].push(input);

  map.addListener('bounds_changed', function() {
    searchBox.setBounds(map.getBounds());
  });

  let markers = [];

  searchBox.addListener('places_changed', function() {
    let places = searchBox.getPlaces();

    if (places.length == 0) {
      return;
    }

    markers.forEach(function(marker) {
      marker.setMap(null);
    });
    markers = [];

    let bounds = new google.maps.LatLngBounds();
    places.forEach(function(place) {
      if (!place.geometry) {
        console.log("Returned place contains no geometry");
        return;
      }

      let icon = {
        url: place.icon,
        size: new google.maps.Size(71, 71),
        origin: new google.maps.Point(0, 0),
        anchor: new google.maps.Point(17, 34),
        scaledSize: new google.maps.Size(25, 25)
      };

      markers.push(new google.maps.Marker({
        map: map,
        icon: icon,
        title: place.name,
        position: place.geometry.location
      }));

      if (place.geometry.viewport) {
        bounds.union(place.geometry.viewport);
      } else {
        bounds.extend(place.geometry.location);
      }
    });

    map.fitBounds(bounds);
  });
}

/* Always set the map height explicitly to define the size of the div
 * element that contains the map. */

#map {
  height: 90%;
}

/* Optional: Makes the sample page fill the window. */

html,
body {
  height: 100%;
  margin: 0;
  padding: 0;
}

#description {
  font-family: Roboto;
  font-size: 15px;
  font-weight: 300;
}

#infowindow-content .title {
  font-weight: bold;
}

#infowindow-content {
  display: none;
}

#map #infowindow-content {
  display: inline;
}

.pac-card {
  margin: 10px 10px 0 0;
  border-radius: 2px 0 0 2px;
  box-sizing: border-box;
  -moz-box-sizing: border-box;
  outline: none;
  box-shadow: 0 2px 6px rgba(0, 0, 0, 0.3);
  background-color: #fff;
  font-family: Roboto;
}

#pac-container {
  padding-bottom: 12px;
  margin-right: 12px;
}

.pac-controls {
  display: inline-block;
  padding: 5px 11px;
}

.pac-controls label {
  font-family: Roboto;
  font-size: 13px;
  font-weight: 300;
}

#pac-input {
  background-color: #fff;
  font-family: Roboto;
  font-size: 15px;
  font-weight: 300;
  margin-left: 12px;
  padding: 0 11px 0 13px;
  text-overflow: ellipsis;
  width: 400px;
}

#pac-input:focus {
  border-color: #4d90fe;
}

#title {
  color: #fff;
  background-color: #4d90fe;
  font-size: 25px;
  font-weight: 500;
  padding: 6px 12px;
}

<div id="pac-container">
  <input id="pac-input" type="text" placeholder="Enter a location" value="starbuck near New York city">
</div>
<div id="map"></div>
<div id="infowindow-content">
  <img src="" width="16" height="16" id="place-icon">
  <span id="place-name" class="title"></span><br>
  <span id="place-address"></span>
</div>
<!-- Replace the value of the key parameter with your own API key. -->
<script src="https://maps.googleapis.com/maps/api/js?key=AIzaSyCkUOdZ5y7hMm0yrcCQoCvLwzdM6M8s5qk&libraries=places&callback=initAutocomplete" async defer></script>


答:
You could do something like this - </p>

```<code>def index
  messages = Message.where(recipient_id: id)
                .select('DISTINCT ON ("chat_id") *, created_at')
                .order(:chat_id, created_at)
                .sort_by(&:created_at).reverse
end
</code>```

Title: Rails: order the results returned from DISTINCT ON * ORDER

Body:
You could do something like this -

def index
  messages = Message.where(recipient_id: id)
                .select('DISTINCT ON ("chat_id") *, created_at')
                .order(:chat_id, created_at)
                .sort_by(&:created_at).reverse
end


问:
How to actually make lombok annotations work for getters and setter
I am trying to use lombok getters and setters annotations.
As far as I know the annotated code is generated at runtime and not compile time so how can take the help of autogenerated getters and setters for writing code?

for example I have a class like this

```<code>@lombok.Getters
@lombok.Setters
public class MyLombokTesting {

private String userName;

}
</code>```

but what is the use of such annotations if these are not generated while writing code...

Now I want to do something like this

```<code>MyLombokTesting myLombokTesting = new MyLombokTesting();
String username = myLombokTesting.getUserName();
or myLombokTesting.setUserName("some username");
</code>```

but I can't do any of these since there are no setters and getters generated for me in eclipse while writing code..

Obviously I can have a one argument constructor to set the username but what about getter?

答:
I use Eclipse IDE. I have to install lombok in my computer before adding lombok library in pom.xml

Step 1:
- Download lombok at https://projectlombok.org/download
- Run command java -jar

- Restart your IDE
- Finish

Step 2:
- Add lombok to pom.xml file

```<code><dependency>
    <groupId>org.projectlombok</groupId>
    <artifactId>lombok</artifactId>
    <version>1.18.8</version>
    <scope>provided</scope>
</dependency>
</code>```

call getter / setter in your code

Body:
I am trying to use lombok getters and setters annotations.
As far as I know the annotated code is generated at runtime and not compile time so how can take the help of autogenerated getters and setters for writing code?

for example I have a class like this

@lombok.Getters
@lombok.Setters
public class MyLombokTesting {

private String userName;

}

but what is the use of such annotations if these are not generated while writing code...

Now I want to do something like this

MyLombokTesting myLombokTesting = new MyLombokTesting();
String username = myLombokTesting.getUserName();
or myLombokTesting.setUserName("some username");

but I can't do any of these since there are no setters and getters generated for me in eclipse while writing code..

Obviously I can have a one argument constructor to set the username but what about getter?

Body:
I use Eclipse IDE. I have to install lombok in my computer before adding lombok library in pom.xml

Step 1:
- Download lombok at https://projectlombok.org/download
- Run command java -jar

- Restart your IDE
- Finish

Step 2:
- Add lombok to pom.xml file

<dependency>
    <groupId>org.projectlombok</groupId>
    <artifactId>lombok</artifactId>
    <version>1.18.8</version>
    <scope>provided</scope>
</dependency>

call getter / setter in your code


问:
mkdocs nav title different from page title
My mkdocs.yml file has nav titles that are shortened to fit onto only 1 line each in the left-side navigation, and I want the .md Markdown page title to be the un-abbreviated full-length title.

For example, while my mkdocs.yml file contains:

```<code>nav:
- BD, ML, DS: Big_Data,_Machine_Learning,_Data_Science.md
- AI, VI: Artificial_Intelligence,_Video_Intelligence.md
</code>```

I want the .md page title to be:

```<code>Big Data, Machine Learning, and Data Science
</code>```

...instead of copying/using the mkdocs.yml nav title:

```<code>BD, ML, DS
</code>```

When I added the Markdown Page Title to the 1st line (# Big Data...) of my .md file, I get both the page title I want and the inherited mkdocs.yml nav title:

```<code>BD, ML, DS
7 min (1,939 words)
Big Data, Machine Learning, and Data Science
</code>```

It seems the answer is in the mkdocs.yml file to specify a different/second "page display" name, but many Google searches have turned up nothing.

What other methods have you tried or heard of? Thanks!

答:
This is only possible with a custom theme which specifically adds support for such a feature. However I am not aware of any themes which offer such a feature.

A page can only have one title. However, the page title can be defined in any one of four ways as documented:

MkDocs will attempt to determine the title of a document in the
  following ways, in order:

A title defined in the nav configuration setting for a document.

A title defined in the title meta-data key of a document.

A level 1 Markdown header on the first line of the document body.

The filename of a document.

Upon finding a title for a page, MkDoc does not continue checking any
  additional sources in the above list.

That last sentence is the key to making this work. As MkDocs is finding a title defined in the nav configuration of your mkdocs.yml config file, it never checks for a title defined anywhere else (including in meta data). It simply uses the nav title for the page as the page title everywhere (in the page.title attribute).

However, the meta-data for the page is still saved under the page.meta attribute. Therefore, you can use page.title in the nav section of your custom theme and page.meta.title anywhere else in your theme.

To define meta-data for a page, add a YAML section to the beginning of the Markdown file:

```<code>---
title: Big Data, Machine Learning, and Data Science
---

The first line of your Markdown.
</code>```

Of course, define a title in your config file as before:

```<code>nav:
- 'BD, ML, DS': 'Big_Data,_Machine_Learning,_Data_Science.md'
</code>```

Then in your theme you can use page.title where you want BD, ML, DS to appear and page.meta.title where you want Big Data, Machine Learning, and Data Science to appear.

If you don't want to have to create an entire new theme from scratch, you might be able to combine a custom_dir and template blocks to override only specific sections of your theme of choice.

Body:
My mkdocs.yml file has nav titles that are shortened to fit onto only 1 line each in the left-side navigation, and I want the .md Markdown page title to be the un-abbreviated full-length title.

For example, while my mkdocs.yml file contains:

nav:
- BD, ML, DS: Big_Data,_Machine_Learning,_Data_Science.md
- AI, VI: Artificial_Intelligence,_Video_Intelligence.md

I want the .md page title to be:

Big Data, Machine Learning, and Data Science

...instead of copying/using the mkdocs.yml nav title:

BD, ML, DS

When I added the Markdown Page Title to the 1st line (# Big Data...) of my .md file, I get both the page title I want and the inherited mkdocs.yml nav title:

BD, ML, DS
7 min (1,939 words)
Big Data, Machine Learning, and Data Science

It seems the answer is in the mkdocs.yml file to specify a different/second "page display" name, but many Google searches have turned up nothing.

What other methods have you tried or heard of? Thanks!

Body:
This is only possible with a custom theme which specifically adds support for such a feature. However I am not aware of any themes which offer such a feature.

A page can only have one title. However, the page title can be defined in any one of four ways as documented:

MkDocs will attempt to determine the title of a document in the
  following ways, in order:

A title defined in the nav configuration setting for a document.

A title defined in the title meta-data key of a document.

A level 1 Markdown header on the first line of the document body.

The filename of a document.

Upon finding a title for a page, MkDoc does not continue checking any
  additional sources in the above list.

That last sentence is the key to making this work. As MkDocs is finding a title defined in the nav configuration of your mkdocs.yml config file, it never checks for a title defined anywhere else (including in meta data). It simply uses the nav title for the page as the page title everywhere (in the page.title attribute).

However, the meta-data for the page is still saved under the page.meta attribute. Therefore, you can use page.title in the nav section of your custom theme and page.meta.title anywhere else in your theme.

To define meta-data for a page, add a YAML section to the beginning of the Markdown file:

---
title: Big Data, Machine Learning, and Data Science
---

The first line of your Markdown.

Of course, define a title in your config file as before:

nav:
- 'BD, ML, DS': 'Big_Data,_Machine_Learning,_Data_Science.md'

Then in your theme you can use page.title where you want BD, ML, DS to appear and page.meta.title where you want Big Data, Machine Learning, and Data Science to appear.

If you don't want to have to create an entire new theme from scratch, you might be able to combine a custom_dir and template blocks to override only specific sections of your theme of choice.


问:
Collapsing all inner braces in Visual Studio 2019
Suppose we have something like this:

```<code>{                      // 1
    A();
    {                  // 1.1
        B();
        {              // 1.1.1
            {          // 1.1.1.1
                D();
            }
            X();
            {          // 1.1.1.2
                E();
            }
        }
        C();
        {              // 1.1.2
            F();
        }
    }
}
</code>```

And we'd like to collapse block 1.1.1 along with all the blocks in it to get:

```<code>{                      // 1
    A();
    {                  // 1.1
        B();
        {...}          // 1.1.1
        //  {...}         1.1.1.1 also collapsed in 1.1.1
        //  X();
        //  {...}         1.1.1.2 also collapsed in 1.1.2
        C();
        {              // 1.1.2
            F();
        }
    }
}
</code>```

Is there a way to do it quickly (esp. in case of multiple layers of sub-blocks)?

I know of CTRL+M+L, which I tend to use quite often, and would love to learn more.

Have a good day.

答:
The feauture I was looking for was in Edit.Outlining.Collapse All in:

It seems to not have a shortcut assigned by default, so

I went to Tools.Options...

Then in the left panel select Environment > Keyboard

Find Edit.CollapseAllincurrentblock on the right

In editbox "Press shortcut keys", pressed CTRL+M, CTRL+B in order

In "Use new shortcut in:", I used Global

Click Assign

Done.

Now, if you're in a block, clicking CTRL+M followed by CTRL+B should collapse all blocks in current block. The only missing part is that the current block itself remains expanded, but that can be fixed with CTRL+M, CTRL+S (collapse current region, which collapses the current block, but not inner blocks).

Body:
Suppose we have something like this:

{                      // 1
    A();
    {                  // 1.1
        B();
        {              // 1.1.1
            {          // 1.1.1.1
                D();
            }
            X();
            {          // 1.1.1.2
                E();
            }
        }
        C();
        {              // 1.1.2
            F();
        }
    }
}

And we'd like to collapse block 1.1.1 along with all the blocks in it to get:

{                      // 1
    A();
    {                  // 1.1
        B();
        {...}          // 1.1.1
        //  {...}         1.1.1.1 also collapsed in 1.1.1
        //  X();
        //  {...}         1.1.1.2 also collapsed in 1.1.2
        C();
        {              // 1.1.2
            F();
        }
    }
}

Is there a way to do it quickly (esp. in case of multiple layers of sub-blocks)?

I know of CTRL+M+L, which I tend to use quite often, and would love to learn more.

Have a good day.


问:
Share session between two .NET Core app and .NET Framework app different application pool same domain using azure ad - IDX20804 error
I have a .NET Core application and another .NET Framework application running under the same site (domain) on IIS. Both are working perfectly. But when I add authentication with azure ad on the .NET Core app, I am having some errors (shown below).

.NET Framework app specs:

Already using authentication with SAML 2.0

Nothing has been changed in this application

Has its own web.config file

Has its own application pool

Login working fine

.NET Core app specs:

Using .net core 3.1

Using Azure AD to authenticate the user

TenantId and ClientId are setted correctly in appsettings.json file

Has its own web.config file

Has its own application pool

Login working fine locally (with visual studio using iis express) authentication with azure Ad

IIS site structure - screenshot

Application pools - screenshot

Steps :

Login sucessfully with saml

Get in the .NET Framework app sucessfully

Click on the .net core app

Loads for a while and get 3 errors :

```<code>
An unhandled exception has occurred while executing the request.

Exception:
System.InvalidOperationException: IDX20803: Unable to obtain configuration from: 'https://login.microsoftonline.com/blablabla/.well-known/openid-configuration'.
 ---> System.IO.IOException: IDX20804: Unable to retrieve document from: 'https://login.microsoftonline.com/blablabla/.well-known/openid-configuration'.
 ---> System.Threading.Tasks.TaskCanceledException: The operation was canceled.
   at System.Net.Http.ConnectHelper.ConnectAsync(String host, Int32 port, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.ConnectAsync(HttpRequestMessage request, Boolean allowHttp2, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.CreateHttp11ConnectionAsync(HttpRequestMessage request, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.GetHttpConnectionAsync(HttpRequestMessage request, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.SendWithRetryAsync(HttpRequestMessage request, Boolean doRequestAuth, CancellationToken cancellationToken)
   at System.Net.Http.RedirectHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
   at System.Net.Http.DiagnosticsHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
   at System.Net.Http.HttpClient.FinishSendAsyncBuffered(Task`1 sendTask, HttpRequestMessage request, CancellationTokenSource cts, Boolean disposeCts)
   at Microsoft.IdentityModel.Protocols.HttpDocumentRetriever.GetDocumentAsync(String address, CancellationToken cancel)
   --- End of inner exception stack trace ---
   at Microsoft.IdentityModel.Protocols.HttpDocumentRetriever.GetDocumentAsync(String address, CancellationToken cancel)
   at Microsoft.IdentityModel.Protocols.OpenIdConnect.OpenIdConnectConfigurationRetriever.GetAsync(String address, IDocumentRetriever retriever, CancellationToken cancel)
   at Microsoft.IdentityModel.Protocols.ConfigurationManager`1.GetConfigurationAsync(CancellationToken cancel)
   --- End of inner exception stack trace ---
   at Microsoft.IdentityModel.Protocols.ConfigurationManager`1.GetConfigurationAsync(CancellationToken cancel)
   at Microsoft.AspNetCore.Authentication.OpenIdConnect.OpenIdConnectHandler.HandleChallengeAsyncInternal(AuthenticationProperties properties)
   at Microsoft.AspNetCore.Authentication.OpenIdConnect.OpenIdConnectHandler.HandleChallengeAsync(AuthenticationProperties properties)
   at Microsoft.AspNetCore.Authentication.AuthenticationHandler`1.ChallengeAsync(AuthenticationProperties properties)
   at Microsoft.AspNetCore.Authentication.AuthenticationService.ChallengeAsync(HttpContext context, String scheme, AuthenticationProperties properties)
   at Microsoft.AspNetCore.Mvc.ChallengeResult.ExecuteResultAsync(ActionContext context)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeAlwaysRunResultFilters>g__Awaited|26_0(ResourceInvoker invoker, Task lastTask, State next, Scope scope, Object state, Boolean isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeFilterPipelineAsync>g__Awaited|19_0(ResourceInvoker invoker, Task lastTask, State next, Scope scope, Object state, Boolean isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeAsync>g__Awaited|17_0(ResourceInvoker invoker, Task task, IDisposable scope)
   at Microsoft.AspNetCore.Routing.EndpointMiddleware.<Invoke>g__AwaitRequestTask|6_0(Endpoint endpoint, Task requestTask, ILogger logger)
   at Microsoft.AspNetCore.Authorization.AuthorizationMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Authentication.AuthenticationMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware.Invoke(HttpContext context)
</code>```

Before getting the above errors logs, in the event viewer I have some warnings :

```<code>EventId: 50

Using an in-memory repository. Keys will not be persisted to storage.
</code>```

```<code>Category: Microsoft.AspNetCore.DataProtection.KeyManagement.XmlKeyManager
EventId: 59

Neither user profile nor HKLM registry available. Using an ephemeral key repository. Protected data will be unavailable when application exits.
</code>```

```<code>Category: Microsoft.AspNetCore.DataProtection.KeyManagement.XmlKeyManager
EventId: 35

No XML encryptor configured. Key {blablabla} may be persisted to storage in unencrypted form.
</code>```

Not sure about what are these warnings. Maybe they can maybe guide to the right problem.

Also, this is the last log before the error log which shows that the app is successfully started.

```<code>Application 'X:\inetpub\wwwroot\MyApp\' started successfully.
</code>```

I assumed they were able to share the session between the two applications since they are under the same domain.

Is there something missing ?

答:
No, they are not. to share session between application, the key point is to share cookie between cookie, not under the same domain. and the key point to share cookie is the same key to encrypt and decrypt data,just like what you see in the event viewer. The reason is that session will use a aspnet.session cookie to track every connection's session, this cookie is encrypted by asp.net core. To enable to share session between application, your application should be able to share the key to decrypt and encrypt data. these part in asp.net core is called data protection. looks you have not configured the data protection key.
You can refer to this document for more detail</p>

Body:
I have a .NET Core application and another .NET Framework application running under the same site (domain) on IIS. Both are working perfectly. But when I add authentication with azure ad on the .NET Core app, I am having some errors (shown below).

.NET Framework app specs:

Already using authentication with SAML 2.0

Nothing has been changed in this application

Has its own web.config file

Has its own application pool

Login working fine

.NET Core app specs:

Using .net core 3.1

Using Azure AD to authenticate the user

TenantId and ClientId are setted correctly in appsettings.json file

Has its own web.config file

Has its own application pool

Login working fine locally (with visual studio using iis express) authentication with azure Ad

IIS site structure - screenshot

Application pools - screenshot

Steps :

Login sucessfully with saml

Get in the .NET Framework app sucessfully

Click on the .net core app

Loads for a while and get 3 errors :

An unhandled exception has occurred while executing the request.

Exception:
System.InvalidOperationException: IDX20803: Unable to obtain configuration from: 'https://login.microsoftonline.com/blablabla/.well-known/openid-configuration'.
 ---> System.IO.IOException: IDX20804: Unable to retrieve document from: 'https://login.microsoftonline.com/blablabla/.well-known/openid-configuration'.
 ---> System.Threading.Tasks.TaskCanceledException: The operation was canceled.
   at System.Net.Http.ConnectHelper.ConnectAsync(String host, Int32 port, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.ConnectAsync(HttpRequestMessage request, Boolean allowHttp2, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.CreateHttp11ConnectionAsync(HttpRequestMessage request, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.GetHttpConnectionAsync(HttpRequestMessage request, CancellationToken cancellationToken)
   at System.Net.Http.HttpConnectionPool.SendWithRetryAsync(HttpRequestMessage request, Boolean doRequestAuth, CancellationToken cancellationToken)
   at System.Net.Http.RedirectHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
   at System.Net.Http.DiagnosticsHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
   at System.Net.Http.HttpClient.FinishSendAsyncBuffered(Task`1 sendTask, HttpRequestMessage request, CancellationTokenSource cts, Boolean disposeCts)
   at Microsoft.IdentityModel.Protocols.HttpDocumentRetriever.GetDocumentAsync(String address, CancellationToken cancel)
   --- End of inner exception stack trace ---
   at Microsoft.IdentityModel.Protocols.HttpDocumentRetriever.GetDocumentAsync(String address, CancellationToken cancel)
   at Microsoft.IdentityModel.Protocols.OpenIdConnect.OpenIdConnectConfigurationRetriever.GetAsync(String address, IDocumentRetriever retriever, CancellationToken cancel)
   at Microsoft.IdentityModel.Protocols.ConfigurationManager`1.GetConfigurationAsync(CancellationToken cancel)
   --- End of inner exception stack trace ---
   at Microsoft.IdentityModel.Protocols.ConfigurationManager`1.GetConfigurationAsync(CancellationToken cancel)
   at Microsoft.AspNetCore.Authentication.OpenIdConnect.OpenIdConnectHandler.HandleChallengeAsyncInternal(AuthenticationProperties properties)
   at Microsoft.AspNetCore.Authentication.OpenIdConnect.OpenIdConnectHandler.HandleChallengeAsync(AuthenticationProperties properties)
   at Microsoft.AspNetCore.Authentication.AuthenticationHandler`1.ChallengeAsync(AuthenticationProperties properties)
   at Microsoft.AspNetCore.Authentication.AuthenticationService.ChallengeAsync(HttpContext context, String scheme, AuthenticationProperties properties)
   at Microsoft.AspNetCore.Mvc.ChallengeResult.ExecuteResultAsync(ActionContext context)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeAlwaysRunResultFilters>g__Awaited|26_0(ResourceInvoker invoker, Task lastTask, State next, Scope scope, Object state, Boolean isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeFilterPipelineAsync>g__Awaited|19_0(ResourceInvoker invoker, Task lastTask, State next, Scope scope, Object state, Boolean isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeAsync>g__Awaited|17_0(ResourceInvoker invoker, Task task, IDisposable scope)
   at Microsoft.AspNetCore.Routing.EndpointMiddleware.<Invoke>g__AwaitRequestTask|6_0(Endpoint endpoint, Task requestTask, ILogger logger)
   at Microsoft.AspNetCore.Authorization.AuthorizationMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Authentication.AuthenticationMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware.Invoke(HttpContext context)

Before getting the above errors logs, in the event viewer I have some warnings :

EventId: 50

Using an in-memory repository. Keys will not be persisted to storage.

Category: Microsoft.AspNetCore.DataProtection.KeyManagement.XmlKeyManager
EventId: 59

Neither user profile nor HKLM registry available. Using an ephemeral key repository. Protected data will be unavailable when application exits.

Category: Microsoft.AspNetCore.DataProtection.KeyManagement.XmlKeyManager
EventId: 35

No XML encryptor configured. Key {blablabla} may be persisted to storage in unencrypted form.

Not sure about what are these warnings. Maybe they can maybe guide to the right problem.

Also, this is the last log before the error log which shows that the app is successfully started.

Application 'X:\inetpub\wwwroot\MyApp\' started successfully.

I assumed they were able to share the session between the two applications since they are under the same domain.

Is there something missing ?


问:
How can I call a function on a button being enabled in Angular 8?
Below is a snippet of my sign-in.component.html file. I have a function within the corresponding sign-in.component.ts file which I would like to call on the button below becoming enabled. An example of what I hope to achieve:</p>

```<code><div class="button-container">
    <button mat-raised-button [disabled]="!signInForm.valid" (enabled)="callAFunction()" type="submit">Sign in</button>
</div>
</code>```

答:
In your ngOnInit function, subscribe on signInForm.valueChanges to call callAFunction().

ngOnInit(){
  this.signInForm.valueChanges.subscribe(v => {
    if (this.signInForm.valid) {
      callAFunction();
    }
  })
}
```

Body:
Below is a snippet of my sign-in.component.html file. I have a function within the corresponding sign-in.component.ts file which I would like to call on the button below becoming enabled. An example of what I hope to achieve:

    <button mat-raised-button [disabled]="!signInForm.valid" (enabled)="callAFunction()" type="submit">Sign in</button>


问:
How to correctly scale custom thumb for a switch widget?
I've a custom thumb set from a drawable for a Switch widget inside a LinearLayout. I can't get it to show correctly on all kinds of screens. On most screens, it looks like this-

Which is fine, but on some screens (example - 440 dpi), it'd look like this-

How do I get this to look uniform across all screens? I've tried many things, including switchMinWidth, setting android:width= to 0dp, using thumbTextPadding but nothing works. Everything has the exact same result, it works on some screens but not on others.

Here's my Switch widget placed inside a LinearLayout with a layout_weight of 2. There are usually 5 widgets in each Horizontal LinearLayout but this specific one has 4 as Switch is supposed to take 2 slots.

        <Switch
            android:id="@+id/btndegreerad"
            style="?android:attr/borderlessButtonStyle"
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="2"
            android:background="@drawable/degree_rad_track"
            android:showText="true"
            android:switchTextAppearance="@style/SwitchTextTheme"
            android:textAppearance="@style/TextAppearance.AppCompat.Body1"
            android:textOff="@string/btnrad"
            android:textOn="@string/btndegree"
            android:thumb="@drawable/degree_rad_thumb"
            android:thumbTextPadding="@dimen/_3sdp"
            android:thumbTint="@color/colorSwitch"
            android:track="@drawable/degree_rad_track" />
```

<p>Here's the <code>degree_rad_thumb</code> drawable-</p>

<pre class="lang-xml prettyprint-override"><code><?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_checked="false">
        <shape android:shape="rectangle">
            <size android:height="@dimen/_38sdp" android:width="0dp"/>
            <corners android:bottomRightRadius="10dp"
                android:bottomLeftRadius="10dp"
                android:topRightRadius="10dp"
                android:topLeftRadius="10dp"/>
        </shape>
    </item>
    <item android:state_checked="true">
        <shape android:shape="rectangle">
            <size android:height="@dimen/_38sdp" android:width="0dp"/>
            <corners android:bottomRightRadius="10dp"
                android:bottomLeftRadius="10dp"
                android:topRightRadius="10dp"
                android:topLeftRadius="10dp"/>
        </shape>
    </item>
</selector>
</code>```

Here's also degree_rad_track, though this is probably not needed-

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_checked="false">
        <shape android:shape="rectangle">
            <solid android:color="@color/colorFadedPrimary"/>
            <corners android:bottomRightRadius="10dp"
                android:bottomLeftRadius="10dp"
                android:topRightRadius="10dp"
                android:topLeftRadius="10dp"/>
        </shape>
    </item>
    <item android:state_checked="true">
        <shape android:shape="rectangle">
            <solid android:color="@color/colorFadedPrimary"/>
            <corners android:bottomRightRadius="10dp"
                android:bottomLeftRadius="10dp"
                android:topRightRadius="10dp"
                android:topLeftRadius="10dp"/>
        </shape>
    </item>
</selector>
```

答:
If you want to correctly scale to all screens on anything; My best rules are using ScrollView and RelativeLayout/ConstraintLayout in general so it's usable and scales.

You can choose between ConstraintLayout and RelativeLayout; Both should scale correctly, perhaps Relative is easier since you don't have to set the constraints. ScrollView isn't necessarily needed here since we don't have a lot of data.

Try putting your Switch inside a RelativeLayout/ConstraintLayout and it should work.

```<code>        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical">

            <RelativeLayout
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:orientation="vertical">

                <Switch
                    android:id="@+id/btndegreerad"
                    style="?android:attr/borderlessButtonStyle"
                    android:layout_width="0dp"
                    android:layout_height="match_parent"
                    android:layout_weight="2"
                    android:background="@drawable/degree_rad_track"
                    android:showText="true"
                    android:switchTextAppearance="@style/SwitchTextTheme"
                    android:textAppearance="@style/TextAppearance.AppCompat.Body1"
                    android:textOff="@string/btnrad"
                    android:textOn="@string/btndegree"
                    android:thumb="@drawable/degree_rad_thumb"
                    android:thumbTextPadding="@dimen/_3sdp"
                    android:thumbTint="@color/colorSwitch"
                    android:track="@drawable/degree_rad_track" />

            </RelativeLayout>

        </LinearLayout>
</code>```

Note: Customise the layouts as you want

Hope it helps.

Body:
I've a custom thumb set from a drawable for a Switch widget inside a LinearLayout. I can't get it to show correctly on all kinds of screens. On most screens, it looks like this-

Which is fine, but on some screens (example - 440 dpi), it'd look like this-

How do I get this to look uniform across all screens? I've tried many things, including switchMinWidth, setting android:width= to 0dp, using thumbTextPadding but nothing works. Everything has the exact same result, it works on some screens but not on others.

Here's my Switch widget placed inside a LinearLayout with a layout_weight of 2. There are usually 5 widgets in each Horizontal LinearLayout but this specific one has 4 as Switch is supposed to take 2 slots.

        <Switch
            android:id="@+id/btndegreerad"
            style="?android:attr/borderlessButtonStyle"
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="2"
            android:background="@drawable/degree_rad_track"
            android:showText="true"
            android:switchTextAppearance="@style/SwitchTextTheme"
            android:textAppearance="@style/TextAppearance.AppCompat.Body1"
            android:textOff="@string/btnrad"
            android:textOn="@string/btndegree"
            android:thumb="@drawable/degree_rad_thumb"
            android:thumbTextPadding="@dimen/_3sdp"
            android:thumbTint="@color/colorSwitch"
            android:track="@drawable/degree_rad_track" />

Here's the degree_rad_thumb drawable-

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_checked="false">
        <shape android:shape="rectangle">
            <size android:height="@dimen/_38sdp" android:width="0dp"/>
            <corners android:bottomRightRadius="10dp"
                android:bottomLeftRadius="10dp"
                android:topRightRadius="10dp"
                android:topLeftRadius="10dp"/>
        </shape>
    </item>
    <item android:state_checked="true">
        <shape android:shape="rectangle">
            <size android:height="@dimen/_38sdp" android:width="0dp"/>
            <corners android:bottomRightRadius="10dp"
                android:bottomLeftRadius="10dp"
                android:topRightRadius="10dp"
                android:topLeftRadius="10dp"/>
        </shape>
    </item>
</selector>

Here's also degree_rad_track, though this is probably not needed-

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_checked="false">
        <shape android:shape="rectangle">
            <solid android:color="@color/colorFadedPrimary"/>
            <corners android:bottomRightRadius="10dp"
                android:bottomLeftRadius="10dp"
                android:topRightRadius="10dp"
                android:topLeftRadius="10dp"/>
        </shape>
    </item>
    <item android:state_checked="true">
        <shape android:shape="rectangle">
            <solid android:color="@color/colorFadedPrimary"/>
            <corners android:bottomRightRadius="10dp"
                android:bottomLeftRadius="10dp"
                android:topRightRadius="10dp"
                android:topLeftRadius="10dp"/>
        </shape>
    </item>
</selector>

Body:
If you want to correctly scale to all screens on anything; My best rules are using ScrollView and RelativeLayout/ConstraintLayout in general so it's usable and scales.

You can choose between ConstraintLayout and RelativeLayout; Both should scale correctly, perhaps Relative is easier since you don't have to set the constraints. ScrollView isn't necessarily needed here since we don't have a lot of data.

Try putting your Switch inside a RelativeLayout/ConstraintLayout and it should work.

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical">

            <RelativeLayout
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:orientation="vertical">

                <Switch
                    android:id="@+id/btndegreerad"
                    style="?android:attr/borderlessButtonStyle"
                    android:layout_width="0dp"
                    android:layout_height="match_parent"
                    android:layout_weight="2"
                    android:background="@drawable/degree_rad_track"
                    android:showText="true"
                    android:switchTextAppearance="@style/SwitchTextTheme"
                    android:textAppearance="@style/TextAppearance.AppCompat.Body1"
                    android:textOff="@string/btnrad"
                    android:textOn="@string/btndegree"
                    android:thumb="@drawable/degree_rad_thumb"
                    android:thumbTextPadding="@dimen/_3sdp"
                    android:thumbTint="@color/colorSwitch"
                    android:track="@drawable/degree_rad_track" />

            </RelativeLayout>

        </LinearLayout>

Note: Customise the layouts as you want

Hope it helps.


问:
setDisplayHomeAsUpEnabled not working in one of my Activities but everywhere else it does work
For some reason this doesn't work in one of my activities but everywhere else it works fine when i press the back arrow in the toolbar it goes back to my MainActivity.

```<code>import androidx.appcompat.widget.Toolbar;

//Initializing toolbar
mToolbar = findViewById(R.id.mToolbar);
setSupportActionBar(mToolbar);

if((getSupportActionBar() != null)){
    getSupportActionBar().setTitle(R.string.equalizerTitle);
    getSupportActionBar().setDisplayHomeAsUpEnabled(true);
    getSupportActionBar().setHomeAsUpIndicator(R.drawable.ic_home_up);
}
</code>```

Manifest

```<code><activity
     android:name=".activities.EqualizerActivity"
     android:parentActivityName=".activities.MainActivity"
     android:screenOrientation="portrait"/>
</code>```

EDIT

This activity uses a constraint layout as parent but i don't see why this would be the cause, all other activities use RelativeLayout and there they work fine.

答:
Looks like you are using onOptionsItemSelected() method to handle menu buttons. The issue is that the "back" button is also kind of a menu button.

In order for Android to know that you don't have a specific handler for the button and it should be handled by the framework, you need to let Android know it via returning false when you don't "consume" the event. According to the docs:

onOptionsItemSelected()

boolean Return false to allow normal menu processing to proceed, true to consume it here.

So, you should have smth like this:

```<code>public boolean onOptionsItemSelected(MenuItem item) {
       switch (item.getItemId()) {
               case YOUR_BUTTON:
                   // do something
                   return true;
       }
       // By default, allow Android to work on it
       return false;
</code>```

Body:
For some reason this doesn't work in one of my activities but everywhere else it works fine when i press the back arrow in the toolbar it goes back to my MainActivity.

import androidx.appcompat.widget.Toolbar;

//Initializing toolbar
mToolbar = findViewById(R.id.mToolbar);
setSupportActionBar(mToolbar);

if((getSupportActionBar() != null)){
    getSupportActionBar().setTitle(R.string.equalizerTitle);
    getSupportActionBar().setDisplayHomeAsUpEnabled(true);
    getSupportActionBar().setHomeAsUpIndicator(R.drawable.ic_home_up);
}

Manifest

<activity
     android:name=".activities.EqualizerActivity"
     android:parentActivityName=".activities.MainActivity"
     android:screenOrientation="portrait"/>

EDIT

This activity uses a constraint layout as parent but i don't see why this would be the cause, all other activities use RelativeLayout and there they work fine.

Body:
Looks like you are using onOptionsItemSelected() method to handle menu buttons. The issue is that the "back" button is also kind of a menu button.

In order for Android to know that you don't have a specific handler for the button and it should be handled by the framework, you need to let Android know it via returning false when you don't "consume" the event. According to the docs:

onOptionsItemSelected()

boolean Return false to allow normal menu processing to proceed, true to consume it here.

So, you should have smth like this:

public boolean onOptionsItemSelected(MenuItem item) {
       switch (item.getItemId()) {
               case YOUR_BUTTON:
                   // do something
                   return true;
       }
       // By default, allow Android to work on it
       return false;


问:
A* Search for Maze - Infinite Loop When Path does not Exist - Python
I am trying to implement an A-star search algorithm to find a path in a square maze from (0,0) to (dimension - 1, dimension - 1). My algorithm returns the correct path when it exists; however, if there is no path, then it runs in an infinite loop. How do I fix this? For now, I've put a condition to run if the length of the open list exceeds (dimension ^ 4), but this is obviously not a permanent fix. I am using Python 3.7.3. </p>

```<code>import numpy as np

class node():

def __init__(self, parent=None, location=None):
    self.parent = parent
    self.location = location

    self.g = float(0)
    self.h = float(0)
    self.f = float(0)

#returns euclidean distance between two nodes
#takes the locations/tuples of two nodes as arguments
#works properly
def euclidean_distance(node_1, node_2):
    return float((((node_2[1] - node_1[1])**2) + ((node_2[0] - node_1[0])**2))**0.5)

#to make extracting the value at a given location in the maze easier
#takes the maze and two integers as arguments
def get_value(maze, a, b):
    return maze[a][b]

def out_of_bounds(a, b, dim):
    return (a < 0 or a >= dim) or (b < 0 or b >= dim)

#Euclidean A* Search, takes the maze and dimension as arguments
def a_star_euclidean(maze, dim):
    #initializing start node and end node
    start = node(None, (0,0))
    end = node(None, (dim-1, dim-1))

    #initializing open list and closed list
    open_list = []
    closed_list = []
    open_list.append(start)

    while len(open_list) > 0:

        #assigning currentNode
        currentNode = open_list[0]
        currentNode_index = 0

        #current location
        for index, item in enumerate(open_list):
            if item.f < currentNode.f:
                currentNode = item
                currentNode_index = index

        #(currentNode.location)

        row = currentNode.location[0]
        column = currentNode.location[1]

        #updating open list and closed list
        open_list.pop(currentNode_index)
        closed_list.append(currentNode)

        #in case goal node is already reached
        if currentNode.location == end.location:
            path = []
            current = currentNode
            while current is not None:
                path.append(current.location)
                current = current.parent
            #return path[::-1] #returning the path from start to end
            path.reverse()
            return path
        else:
            closed_list.append(currentNode)

        #generating childs
        child_locations = [(row+1, column), (row-1, column), (row, column+1), (row, column-1)]
        #print(child_locations)
        child_nodes = [node(currentNode, location) for location in child_locations]
        #print(child_nodes)

        for child in child_nodes:
            #declaring row and column variables for child nodes
            child_row = int(child.location[0])
            child_column = int(child.location[1])

            if not out_of_bounds(child_row, child_column, dim):

                # Child is on the closed list
                if child in open_list:
                    continue

                #computing g(n), h(n), f(n)
                child.g = float(currentNode.g + 1)
                child.h = float(euclidean_distance(child.location, end.location))
                child.f = float(child.g + child.h)

                #child is in open list
                if child in closed_list:
                    continue

                if get_value(maze, child_row, child_column) == 0:
                    open_list.append(child)
                else:
                    continue

            else:
                continue

        #if (len(open_list) > dim**4): #b^d worst case
            #return None

def main():
    maze = []
    dim = int(input("Enter the dimension of the game: "))
    print(dim)
    for row in range(dim):
        maze.append([])
        for column in range(dim):
            maze[row].append(int(np.random.binomial(1, 0.3, 1)))
    maze[0][0] = 0
    maze[dim-1][dim-1] = 0
    print(maze)
    print("----------")
    print(a_star_euclidean(maze,dim))

    #print(euclidean_distance((1,1), (2,2)))

main()
</code>```

答:
I believe the issue is that child in closed_list is never true, because you haven't overriden the __eq__ operator of the node class. Because of this, python doesn't know how to compare two instances of the node class, so falls back to comparing if they are references to the same object in memory, otherwise it returns false. So two nodes are never equal when searching through closed_list.

Try defining the __eq__ operator for the node class like so. You can change the comparison to include other properties as you need.

class node():
    def __init__(self, parent=None, location=None):
        self.parent = parent
        self.location = location

        self.g = float(0)
        self.h = float(0)
        self.f = float(0)

    def __eq__(self, other):
        return self.location == other.location
```

Body:
I am trying to implement an A-star search algorithm to find a path in a square maze from (0,0) to (dimension - 1, dimension - 1). My algorithm returns the correct path when it exists; however, if there is no path, then it runs in an infinite loop. How do I fix this? For now, I've put a condition to run if the length of the open list exceeds (dimension ^ 4), but this is obviously not a permanent fix. I am using Python 3.7.3.

import numpy as np

class node():

def __init__(self, parent=None, location=None):
    self.parent = parent
    self.location = location

    self.g = float(0)
    self.h = float(0)
    self.f = float(0)

#returns euclidean distance between two nodes
#takes the locations/tuples of two nodes as arguments
#works properly
def euclidean_distance(node_1, node_2):
    return float((((node_2[1] - node_1[1])**2) + ((node_2[0] - node_1[0])**2))**0.5)

#to make extracting the value at a given location in the maze easier
#takes the maze and two integers as arguments
def get_value(maze, a, b):
    return maze[a][b]

def out_of_bounds(a, b, dim):
    return (a < 0 or a >= dim) or (b < 0 or b >= dim)

#Euclidean A* Search, takes the maze and dimension as arguments
def a_star_euclidean(maze, dim):
    #initializing start node and end node
    start = node(None, (0,0))
    end = node(None, (dim-1, dim-1))

    #initializing open list and closed list
    open_list = []
    closed_list = []
    open_list.append(start)

    while len(open_list) > 0:

        #assigning currentNode
        currentNode = open_list[0]
        currentNode_index = 0

        #current location
        for index, item in enumerate(open_list):
            if item.f < currentNode.f:
                currentNode = item
                currentNode_index = index

        #(currentNode.location)

        row = currentNode.location[0]
        column = currentNode.location[1]

        #updating open list and closed list
        open_list.pop(currentNode_index)
        closed_list.append(currentNode)

        #in case goal node is already reached
        if currentNode.location == end.location:
            path = []
            current = currentNode
            while current is not None:
                path.append(current.location)
                current = current.parent
            #return path[::-1] #returning the path from start to end
            path.reverse()
            return path
        else:
            closed_list.append(currentNode)

        #generating childs
        child_locations = [(row+1, column), (row-1, column), (row, column+1), (row, column-1)]
        #print(child_locations)
        child_nodes = [node(currentNode, location) for location in child_locations]
        #print(child_nodes)

        for child in child_nodes:
            #declaring row and column variables for child nodes
            child_row = int(child.location[0])
            child_column = int(child.location[1])

            if not out_of_bounds(child_row, child_column, dim):

                # Child is on the closed list
                if child in open_list:
                    continue

                #computing g(n), h(n), f(n)
                child.g = float(currentNode.g + 1)
                child.h = float(euclidean_distance(child.location, end.location))
                child.f = float(child.g + child.h)

                #child is in open list
                if child in closed_list:
                    continue

                if get_value(maze, child_row, child_column) == 0:
                    open_list.append(child)
                else:
                    continue

            else:
                continue

        #if (len(open_list) > dim**4): #b^d worst case
            #return None

def main():
    maze = []
    dim = int(input("Enter the dimension of the game: "))
    print(dim)
    for row in range(dim):
        maze.append([])
        for column in range(dim):
            maze[row].append(int(np.random.binomial(1, 0.3, 1)))
    maze[0][0] = 0
    maze[dim-1][dim-1] = 0
    print(maze)
    print("----------")
    print(a_star_euclidean(maze,dim))

    #print(euclidean_distance((1,1), (2,2)))

main()


问:
PHP Loop - tweaking an timeline archive page
The archive page of astheria.com is excellent, but have a question regarding the PHP loop used to create it.

The site's author posted the code: Creating a Timeline Style Archive Page

There's a part that I'm unclear on. Should there be a gap in the timeline of more than a year (such as postings for 2007, then nothing for 2008 and 2009, then picking up again in 2010), it looks like this code will print yearly headers (with an empty
).

How might I tweak this to skip these empty years?

答:
The general logic can be as simple as (half-pseudo code):

```<code>$posts = fetchFromDatabase('SELECT * FROM `posts` ORDER BY `posted` DESC');

// $posts = array(
//     array('posted' => '2010-09-13 12:42:31', 'title' => ...)
//     array(...)
// )

$currentYear = null;
foreach ($posts as $post) {
    $year = date('Y', strtotime($post['posted']));
    if ($year != $currentYear) {
        printf('<h2>%s</h2>', $year);
        $currentYear = $year;
    }

    echo $post['title'];
}
</code>```

In words:

Fetch all posts to be displayed from the database sorted by date.

Keep track of the "current year" you're outputting.

Upon entering a new year, output it, update the current year.

That way only the years of existing posts are output.

Body:
The general logic can be as simple as (half-pseudo code):

$posts = fetchFromDatabase('SELECT * FROM `posts` ORDER BY `posted` DESC');

// $posts = array(
//     array('posted' => '2010-09-13 12:42:31', 'title' => ...)
//     array(...)
// )

$currentYear = null;
foreach ($posts as $post) {
    $year = date('Y', strtotime($post['posted']));
    if ($year != $currentYear) {
        printf('<h2>%s</h2>', $year);
        $currentYear = $year;
    }

    echo $post['title'];
}

In words:

Fetch all posts to be displayed from the database sorted by date.

Keep track of the "current year" you're outputting.

Upon entering a new year, output it, update the current year.

That way only the years of existing posts are output.


问:
inet_ntop returning partically incorrect IPv6 address
I am aware of this similar question, but the answers do not make sense and are possibly for a different problem.

In my iOS app I connect to a server using CFSockets and wish to show the remote address of the server. When using IPv4 it works as expected, but there are weird results with IPv6 where the network prefix of the address are correct, but the host bits are completely different.

int sock_fd = <...> // Assume I already have the fd
struct sockaddr addr;
socklen_t addr_len = sizeof(addr);
getpeername(sock_fd, &addr, &addr_len);
char addressString[INET6_ADDRSTRLEN];
inet_ntop(AF_INET6, &((struct sockaddr_in6 *)&addr)->sin6_addr, addressString, INET6_ADDRSTRLEN);
```

<p>What I expected was <code>2607:f2f8:a4c8::2</code> but what I get is an address with the correct network prefix but different host bits each time, e.g:</p>

```               vvvvvvvvvvvvvvvvvvvv Random?
2607:f2f8:a4c8:0:c400:13b0:f6c5:afa
^^^^^^^^^^^^^^ Correct

```

答:
The man page of getpeername(2) gives a hint as to why this is happening:

The address_len parameter should be initialized to indicate the amount of space pointed to by address.  On return it contains the actual size of the address returned (in bytes).

The address is truncated if the buffer provided is too small.

The size of struct sockaddr is too small for IPv6 addresses and will result in the address being truncated.

You need to use struct sockaddr_storage with getpeername rather than just struct sockaddr

struct sockaddr_storage addr;
socklen_t addr_len = sizeof(addr);
getpeername(socket, (struct sockaddr *)&addr, &addr_len)
```

Body:
I am aware of this similar question, but the answers do not make sense and are possibly for a different problem.

In my iOS app I connect to a server using CFSockets and wish to show the remote address of the server. When using IPv4 it works as expected, but there are weird results with IPv6 where the network prefix of the address are correct, but the host bits are completely different.

int sock_fd = <...> // Assume I already have the fd
struct sockaddr addr;
socklen_t addr_len = sizeof(addr);
getpeername(sock_fd, &addr, &addr_len);
char addressString[INET6_ADDRSTRLEN];
inet_ntop(AF_INET6, &((struct sockaddr_in6 *)&addr)->sin6_addr, addressString, INET6_ADDRSTRLEN);

What I expected was 2607:f2f8:a4c8::2 but what I get is an address with the correct network prefix but different host bits each time, e.g:

               vvvvvvvvvvvvvvvvvvvv Random?
2607:f2f8:a4c8:0:c400:13b0:f6c5:afa
^^^^^^^^^^^^^^ Correct